手寫梯度下降擬合二次線性模型

 

這裏用最簡單的Loss Function來推寫一個用梯度下降擬合二次線性模型的代碼

Loss = \sum (\hat{y} - (W_1 * x^2 + W_2 * x + b))^2

首先,我們隨意設計一個二次線性模型:

# 實際曲線
x_orgin = np.linspace(-10,10,100)
y_orgin = 5.0 * x_orgin**2 + 4.0 * x_orgin - 23.0

plt.plot(x_orgin,y_orgin)
plt.show()

接下來我們自己製造一些數據,當然,我們給數據增加一些噪音,使得數據變得沒那麼“準確”,不然我們還擬合啥

# 增加噪音後的實驗數據
x_data = np.array([random.uniform(-10,10) for _ in range(100)])
x_data.sort()
y_data = [5.0 * i**2 + 4.0 * i - 23.0 + random.uniform(-30,30) for i in x_data]

plt.scatter(x_data,y_data)
plt.show()

 最後就是利用梯度下降來尋找參數

x = np.array([random.uniform(-10,10) for _ in range(100)])
y = [5.0 * i**2 + 4.0 * i - 23.0 + random.uniform(-30,30) for i in x]

w1 = 3
w2 = 3
b = 20
lr = 0.0001
iteration = 1000

for _ in range(iteration):
    gd_w1 = 0.0
    gd_w2 = 0.0
    gd_b = 0.0
    for i in range(len(x)):
        gd_w1 += 2.0 * (y[i]-w1*(x[i]**2)-w2*x[i]-b)*(-x[i]*2)
        gd_w2 += 2.0 * (y[i]-w1*(x[i]**2)-w2*x[i]-b)*(-x[i])
        gd_b += 2.0 * (y[i]-w1*(x[i]**2)-w2*x[i]-b)*(-1.0)
#     print(gd_w1,gd_w2,gd_b)

    w1 = w1 - lr*gd_w1
    w2 = w2 - lr*gd_w2
    b = b - lr*gd_b
#     print(w1,w2,b)

x.sort()
y = w1*x**2 + w2*x + b

print(w1, w2, b)
plt.figure()
plt.plot(x,y,color='red')
plt.plot(x_orgin,y_orgin)
plt.scatter(x_data,y_data)
plt.show()

此時的W_1, W_2, b

4.773247363826946   3.886623681913472   -10.806697288331906

紅色的線是擬合的曲線,藍色的線是原始給出的曲線,各個點是增加噪音後的數據集,這裏只訓練了1000次,提高iteration能增加擬合度

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章