Bu listeyi burada gördüm ve en küçük kareleri çözmenin birçok yolu olduğuna inanamadım. Wikipedia'daki "normal denklemler" oldukça basit bir yol gibi görünüyordu:
Öyleyse neden sadece onları kullanmıyorsunuz? Mark L'nin ilk bağlantısında SVD veya QR'nin istatistiksel yazılımda popüler yöntemler olduğunu ve normal denklemlerin "güvenilirlik ve sayısal doğruluk açısından KORKUNÇ" olduğunu belirttiği için bir hesaplama veya kesinlik sorunu olduğunu varsaydım. Ancak , aşağıdaki kodda, normal denklemler üç popüler python fonksiyonu ile karşılaştırıldığında ~ 12 ondalık basamağa doğruluk veriyor: numpy's polyfit ; scipy en linregress ; ve scikit-learn'un LinearRegression'ı .
Daha ilginç olan, n = 100000000 olduğunda normal denklem yönteminin en hızlı olmasıdır. Benim için hesaplama süreleri: Linregress için 2.5s; Polifit için 12.9s; LinearRegression için 4.2'ler; ve normal denklem için 1.8s.
Kod:
import numpy as np
from sklearn.linear_model import LinearRegression
from scipy.stats import linregress
import timeit
b0 = 0
b1 = 1
n = 100000000
x = np.linspace(-5, 5, n)
np.random.seed(42)
e = np.random.randn(n)
y = b0 + b1*x + e
# scipy
start = timeit.default_timer()
print(str.format('{0:.30f}', linregress(x, y)[0]))
stop = timeit.default_timer()
print(stop - start)
# numpy
start = timeit.default_timer()
print(str.format('{0:.30f}', np.polyfit(x, y, 1)[0]))
stop = timeit.default_timer()
print(stop - start)
# sklearn
clf = LinearRegression()
start = timeit.default_timer()
clf.fit(x.reshape(-1, 1), y.reshape(-1, 1))
stop = timeit.default_timer()
print(str.format('{0:.30f}', clf.coef_[0, 0]))
print(stop - start)
# normal equation
start = timeit.default_timer()
slope = np.sum((x-x.mean())*(y-y.mean()))/np.sum((x-x.mean())**2)
stop = timeit.default_timer()
print(str.format('{0:.30f}', slope))
print(stop - start)