线性模型和梯度下降

课程来源:2.线性模型_哔哩哔哩_bilibili

 

线性模型:y=x*w, 绘制权重w和损失函数的图像,使用穷举法找到最适合的权重w。

代码复现: 

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D

#设函数为y=2x+3
x_data = [1.0,2.0,3.0]
y_data = [5.0,7.0,9.0]

def forward(x):
    return x * w + b

def loss(x,y):
    y_pred = forward(x)
    return (y_pred-y)**2

W=np.arange(0.0,4.1,0.1)
B=np.arange(-3.0,8.1,0.1)
#numpy.meshgrid()——生成网格点坐标矩阵
#横坐标矩阵X XX中的每个元素,
# 与纵坐标矩阵Y YY中对应位置元素,共同构成一个点的完整坐标。
# ( X 12 , Y 12 ) = ( 1 , 1 ) (X_{12},Y_{12})


[w,b]=np.meshgrid(W,B)
#w是行向量
print("w",w)
#b是列向量
print("b",b)

l_sum = 0
for x_val, y_val in zip(x_data, y_data):
    #预测值y,不用再使用for遍历w,b的值。
    y_pred_val = forward(x_val)
    print(y_pred_val)
    loss_val = loss(x_val, y_val)
    l_sum += loss_val
    
fig = plt.figure()
ax = Axes3D(fig)
ax.plot_surface(w, b, l_sum/3,cmap="rainbow")
plt.show()

梯度下降算法。

穷举法在数据太多的情况不好用。

使用梯度下降的算法可以找到局部最优解,在凸函数里面效果很好。

以y=x*w为例:

分别定义求预测值y,求数据集的总损失,求梯度的函数:

总损失:均方差1/N\sum_{n=1}^{n}\left ( \widehat{y} -y\right )^{2} 梯度:\frac{\partial cost}{\partial w}=\frac{f(x+\Delta x)-f(x)}{\Delta x}

更新w的值:w=w-\alpha \frac{\partial cost}{\partial w}

权重和损失函数的图像:

 

 输出epoch(测试轮数),w,cost的值,找到使cost取到最小值的w的值。

 

import numpy as np
import matplotlib.pyplot as plt
x_data = [1.0,2.0,3.0]
y_data = [2.0,4.0,6.0]
w=1.0
cost2 = []
epoh1 = []
#求预测值y
def forward (x):
    return w*x
#求cost
def cost(x1,y1):
    cost=0
    for x,y in zip(x1,y1):
        y_ple = forward(x)
        cost += (y_ple-y)**2
    return cost / len(x1)
#求梯度
def gra (x1,y1):
    #2*x*(x*w+b)
    gra=0
    for x,y in zip(x1,y1):
        gra += 2*x*(x*w-y)
    return gra / len(x1)
#变化w的值
for epoh in range(100):
    cost1 = cost(x_data,y_data)
    gra1 = gra(x_data,y_data)
    w-=0.01*gra1
    print("epoh:",epoh,"w:",w,"cost",cost1)
    cost2.append(cost1)
    epoh1.append(epoh)
plt.plot(epoh1,cost2)
plt.ylabel('cost')
plt.xlabel('epoch')
plt.show() 

这里显示的是测试轮数与cost的函数。 

 

 

梯度下降方法有时会进行不了:

在图形左边 :w=w-\alpha \frac{\partial cost}{\partial w}的值基本上不变,可能找不到最优解。

 

为了解决这个情况需要用随机梯度算法:

计算每一个个点的损失loss和梯度,用对应的梯度更新每个点。

loss:\left ( \widehat{y}-y\right )^{2},梯度:2\times \left ( \widehat{y}-y \right )\times x

import numpy as np
import matplotlib.pyplot as plt
import random
x_data = [1,2,3]
y_data = [2,4,6]
w=1
loss2 = []
epoh1 = []
#求预测值y
def forward (x):
    return w*x
#求loss
def loss(x1,y1):
    y_pre=forward (x1)
    loss=(y_pre-y1)**2
    return loss
#求梯度
def gra (x1,y1):
    gra = 2*x1*(x1*w-y1)
    return gra
#变化w的值
for epoh in range(100):
    for xs,ys in zip(x_data,y_data):
        loss1 = loss(xs,ys)
        gra1 = gra(xs,ys)
        w-=0.01*gra1
        print("epoh:",epoh,"w:",w,"loss",loss)
        loss2.append(loss1)
        epoh1.append(epoh)
plt.plot(epoh1,loss2)
plt.ylabel('cost')
plt.xlabel('epoch')
plt.show() 

 

 

梯度下降可以并行计算。(因为cost是一样的,xi和xi+1的梯度只和自己有关,并行计算不影响结果)。

随机梯度下降不可以,但是能找到更好的点。

在实际中采取折中的方法:

若干个一组求相应的梯度,更新w。称为小批量的梯度下降 mini-Batch。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值