神经网络学习笔记(5) – Pytorch深度神经网络计算框架
PyTorch优化器
PyTorch将梯度计算的算法包装成优化器。优化器就是执行迭代更新待训练参数的一个对象。它的使用方式如下:
- 构造优化器,最简单的是传入所有待训练的参数。如果要给某些参数单独设置选项,就需传入一个参数字典。
- 调用backward()计算梯度
- 调用optimizer.step()更新参数值
详细例子可见官网。 PyTorch的优化器在torch.optim这个包下,包括torch.optim.Optimizer,torch.optim.Adadelta,torch.optim.Adagrad,torch.optim.Adam等。
最基本的SGD优化器已经介绍过了,其计算为:
基于动量(Momentum-based)的优化器,能加速梯度方向的下降,使迭代更快收敛。需给定一个在0~1之间的参数momentum_coeff,防止过拟合。其计算如下:
每种优化器各有微妙的变化,有的更复杂,有的有更多hyperparameter,或者更好的性能。目前最常用的是自适应矩估计,即Adam(Adaptive Moment Estimation)优化器。
PyTorch同时也包装了能构建神经网络的层(如线性连接Linear,激活函数ReLU等),以及Loss Function如MSE(均方差)等概念。这些和优化器一起,就能使代码更简洁明了。
import torch
import numpy as np
x_train = np.array ([[4.7], [2.4], [7.5], [7.1], [4.3],
[7.8], [8.9], [5.2], [4.59], [2.1],
[8], [5], [7.5], [5], [4],
[8], [5.2], [4.9], [3], [4.7],
[4], [4.8], [3.5], [2.1], [4.1]],
dtype = np.float32)
y_train = np.array ([[2.6], [1.6], [3.09], [2.4], [2.4],
[3.3], [2.6], [1.96], [3.13], [1.76],
[3.2], [2.1], [1.6], [2.5], [2.2],
[2.75], [2.4], [1.8], [1], [2],
[1.6], [2.4], [2.6], [1.5], [3.1]],
dtype = np.float32)
x = torch.from_numpy(x_train)
y = torch.from_numpy(y_train)
#一个输入,一个输出,5个神经元
inp = 1
hidden = 5
out = 1
model = torch.nn.Sequential(
torch.nn.Linear(inp, hidden), #1个输入->5个神经元的线性层
torch.nn.ReLU(), #ReLU非线性激活函数
torch.nn.Linear(hidden, out)) #5个神经元->1个输出的线性层
#内置的损失函数
loss_fn = torch.nn.MSELoss(reduction='sum')
learning_rate = 1e-4
#使用SGD优化器,传入model的所有参数和learning_rate。经debug可知,PyTorch构造出的模型有5个神经元、1个输出,共6个节点。每个节点有一个相应的b参数,共6个b。共有10个连接,对应10个W。因此总共有16个参数。
optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate)
for i in range(500):
#将输入数据传入model,进行正向传播
y_pred = model(x)
#传入估计值和实际值计算Loss Function
loss = loss_fn(y_pred, y)
#打印Loss Function的值
print(i, loss.item())
#清除权重的梯度
optimizer.zero_grad()
#反向传播
loss.backward()
#更新下一轮迭代的参数值
optimizer.step()
总结
使用PyTorch训练深度神经网络,可抽象为:
- 定义网络各层的节点数(通常输入为特征数,输出为结果数),并用其建立网络模型
- 定义Loss Function
- 定义learning_rate
- 创建优化器(参数包括待优化的模型参数,定义learning_rate,以及该优化器特有的参数)
- 迭代计算模型参数
i. 正向传播
ii. 计算Loss Function
iii. 清空梯度
iv. 反向传播
v. 更新权值