目录
引入
对于普通的梯度下降算法,就是重复正向传播,计算梯度,更新权重的过程。
表示为:
import torch
import torch.nn as nn
class Model(nn.Module):
def __init__(self,in_feature=10,out_feature=3):
super(Model, self).__init__()
self.linear1 = nn.Linear(in_feature,13)
self.linear2 = nn.Linear(13,8)
self.out = nn.Linear(8,out_feature)
def forward(self,x):
z1 = self.linear1(x)
re = torch.relu(z1)
z2 = self.linear2(re)
sigma = torch.sigmoid(z2)
output = self.out(sigma)
# soft = torch.softmax(output,dim=1)
return output
return x_grad
if __name__ == '__main__':
torch.random.manual_seed(22)
x = torch.rand([500,20],dtype=torch.float32)
y = torch.randint(low=0,high=3,size=(500,),dtype=torch.float32)
net = Model(in_feature=x.shape[1],out_feature=len(y.unique()))
zhat = net.forward(x)
criterion = nn.CrossEntropyLoss()
loss = criterion(zhat,y.long())
loss.backward(retain_graph=True)
print(net.linear1.weight.grad)
print(loss)
# renew w
lr = 10# learning_rate
w = net.linear1.weight.data
dw = net.linear1.weight.grad
w -= lr*dw
该过程会消耗较多时间,而时间消耗与步长紧密相关,为了加速迭代过程,优化步长,有了Momentum算法
基本思路
如果下降的方向一直是同一方向,那么使用较长的学习率,一旦方向发生改变,使用较小的学习率,重复这个过程,方向根据过去走过的方向来学习
如何知道历史方向:
上一步方向和更新出来的方向加权求和,得到一个新的方向为当前方向
这里加权求和时,上一步的方向会乘动量参数,真实移动的向量称为“动量”
更新过程
实现
import torch
import torch.nn as nn
import torch.optim as optim
from torch.nn import functional as F
torch.random.manual_seed(22)
x = torch.rand([500,20],dtype=torch.float32)
y = torch.randint(low=0,high=3,size=(500,),dtype=torch.float32)
lr = 0.1 # learning_rate
gamma = 0.9
class Model(nn.Module):
def __init__(self,in_feature=10,out_feature=3):
super(Model, self).__init__()
self.linear1 = nn.Linear(in_feature,13)
self.linear2 = nn.Linear(13,8)
self.out = nn.Linear(8,out_feature)
def forward(self,x):
z1 = self.linear1(x)
re = torch.relu(z1)
z2 = self.linear2(re)
sigma = torch.sigmoid(z2)
output = self.out(sigma)
# soft = torch.softmax(output,dim=1)
return output
return x_grad
if __name__ == '__main__':
net = Model(in_feature=x.shape[1],out_feature=len(y.unique())) # 实例化神经网络
criterion = nn.CrossEntropyLoss()# 定义损失函数(交叉熵
opt = optim.SGD(net.parameters(),lr=lr,momentum=gamma) # 定义优化算法 parameters 一次性导出神经网络架构下全部的权重和截距
"""
梯度下降的流程
1 计算本轮向前传播损失函数值
2 反向传播 得到梯度
3 更新权重和动量
4 清除原来计算出来的,基于上一个点的坐标计算的梯度
"""
zhat = net.forward(x)
loss = criterion(zhat, y.long())
loss.backward(retain_graph=True)
opt.step() # 向前走一步(更新梯度
opt.zero_grad()# 清空之前的梯度
梯度下降的流程
1 计算本轮向前传播损失函数值
2 反向传播 得到梯度
3 更新权重和动量
4 清除原来计算出来的,基于上一个点的坐标计算的梯度
完成上述代码,就可以进行一步的迭代(就是走一步),后面我们来实现走多步
传播过程理解:就是特征值经过前向传播,得到预测的结果,此结果经过选择好的损失函数与真实结果比较得到损失值loss,loss经过反向传播,借由链式法则得到损失函数对于权重w的偏导数@,@此时经过选择好的优化算法来更新权重(比如梯度下降,就会用当前的权重值减去步长与@的积)(对于动量法,会是上一步的权重值 + 优梯度下降更新出的方向和值,然后再得到真实下降的方向。然后“优梯度下降更新出的方向和值” 是上一不的真实方向乘动量参数减去步长乘偏导数。)