temukan garis yang paling sesuai dengan data

Saya mencoba menemukan baris yang paling sesuai dengan data. Saya menggunakan kode berikut di bawah ini tetapi sekarang Saya ingin data ditempatkan ke dalam array yang diurutkan sehingga memiliki data yang paling dekat dengan garis terlebih dahulu bagaimana saya bisa melakukan ini? Apakah polyfit juga merupakan fungsi yang benar untuk digunakan untuk ini?

x=[1,2,2.5,4,5];
y=[1,-1,-.9,-2,1.5];
n=1;
p = polyfit(x,y,n)

f = polyval(p,x);
plot(x,y,'o',x,f,'-')

Gambar

PS: Saya menggunakan Octave 4.0 yang mirip dengan Matlab


person Rick T    schedule 28.02.2017    source sumber


Jawaban (3)


Pertama-tama Anda dapat menghitung kesalahan antara nilai sebenarnya y dan nilai prediksi f

err = abs(y-f);

Kemudian urutkan vektor kesalahannya

[val, idx] = sort(err);

Dan gunakan indeks yang diurutkan untuk mengurutkan nilai y Anda

y2 = y(idx);

Sekarang y2 memiliki nilai yang sama dengan y tetapi yang mendekati nilai pas terlebih dahulu.

Lakukan hal yang sama untuk x untuk menghitung x2 sehingga Anda memiliki korespondensi antara x2 dan y2

x2 = x(idx);
person Sembei Norimaki    schedule 28.02.2017

Sembei Norimaki berhasil menjelaskan pertanyaan utama Anda dengan baik, jadi saya akan melihat pertanyaan kedua Anda = apakah polyfit merupakan fungsi yang tepat?

Garis yang paling cocok didefinisikan sebagai garis yang mempunyai kesalahan rata-rata nol.

Jika harus berupa "garis", kita bisa menggunakan polyfit, yang akan cocok dengan polinomial. Tentu saja, "garis" dapat didefinisikan sebagai polinomial derajat pertama, namun polinomial derajat pertama memiliki beberapa sifat yang membuatnya mudah untuk ditangani. Persamaan polinomial (atau linier) orde pertama yang Anda cari akan berbentuk seperti ini:

y = mx + b

di mana y adalah variabel terikat dan X adalah variabel bebas. Jadi tantangannya adalah ini: temukan m dan b sedemikian rupa sehingga y yang dimodelkan sedekat mungkin dengan y sebenarnya. Ternyata, kesalahan yang terkait dengan kecocokan linier adalah cembung, artinya kesalahan tersebut mempunyai satu nilai minimum. Untuk menghitung nilai minimum ini, cara paling sederhana adalah dengan menggabungkan bias dan vektor x sebagai berikut:

Xcombined = [x.' ones(length(x),1)];

kemudian menggunakan persamaan normal yang diperoleh dari minimalisasi kesalahan

beta = inv(Xcombined.'*Xcombined)*(Xcombined.')*(y.')

bagus, sekarang baris kita didefinisikan sebagai Y = Xcombined*beta. untuk menggambar garis, cukup ambil sampel dari beberapa rentang x dan tambahkan suku b

Xplot = [[0:.1:5].' ones(length([0:.1:5].'),1)];
Yplot = Xplot*beta;
plot(Xplot, Yplot);

Jadi mengapa polyfit bekerja dengan sangat buruk? baiklah, saya tidak bisa memastikannya, tetapi hipotesis saya adalah Anda perlu mengubah urutan matriks x dan y. Saya kira itu akan memberi Anda garis yang lebih masuk akal.

x = x.';
y = y.';

lalu coba

p = polyfit(x,y,n)

Semoga membantu. Seorang bijak pernah mengatakan kepada saya (dan seperti yang saya pelajari setiap hari), jangan percaya pada algoritma yang tidak Anda mengerti!

person David Kaftan    schedule 01.03.2017
comment
x dan y adalah vektor, transposisinya tidak akan berpengaruh. Contoh dalam pertanyaan memiliki hasil regresi yang sangat buruk karena seperti yang Anda lihat, korelasi datanya sangat rendah. Regresi tidak dapat menghasilkan keajaiban, jadi jika Anda ingin memasukkan garis ke dalam data yang berkorelasi rendah, Anda akan mengalami kesalahan besar. Pokoknya nasihat bagus dari orang bijak. - person Sembei Norimaki; 01.03.2017
comment
Ya, melihat ke belakang, aku tidak tahu apa yang kupikirkan. Sama sekali tidak ada alasan untuk menjadikan hal itu menjadi masalah. Saya kira saya pikir ini mungkin memperlakukan set pelatihan sebagai kumpulan data 5 fitur dan 1 sampel. - person David Kaftan; 05.12.2018

Berikut beberapa kode pengujian yang dapat membantu orang lain menangani regresi linier dan kuadrat terkecil

%https://youtu.be/m8FDX1nALSE kode matlab

%https://youtu.be/1C3olrs1CUw video yang bagus untuk dikerjakan secara manual jika Anda ingin mengujinya

function [a0 a1] = rtlinreg(x,y) 
  x=x(:);
  y=y(:);
  n=length(x);
  a1 = (n*sum(x.*y) - sum(x)*sum(y))/(n*sum(x.^2) - (sum(x))^2);  %a1 this is the slope of linear model
  a0 = mean(y) - a1*mean(x); %a0 is the y-intercept
end

x=[65,65,62,67,69,65,61,67]'
y=[105,125,110,120,140,135,95,130]'

[a0 a1] = rtlinreg(x,y);  %a1 is the slope of linear model, a0 is the y-intercept

x_model =min(x):.001:max(x);
y_model = a0 + a1.*x_model;  %y=-186.47 +4.70x   
plot(x,y,'x',x_model,y_model)
person Rick T    schedule 01.03.2017