PyTorch入门——张量&神经网络
张量
直接创建
torch.tensor(data, dtype=None, device=None, requires_grad=False, pin_memory=False)
- data:数据,类型为list、numpy
- dtype:数据类型,默认和data的一致
- device:所在设备,cuda/cpu
- requires_grad:是否需要梯度
- pin_memory:是否存于锁页内存
torch.from_numpy(ndarray) ## 从numpy创建tensor,与原ndarray共享内存
依据数值创建
## 创建全0张量
torch.zeros(*size, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
## 创建全1张量
torch.ones(*size, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
- size:张量的形状
- out:输出的张量
- layout:内存中的布局形式
- device,所在设备,GPU/CPU
- requires_grad:是否需要梯度
## 依input形状创建全0张量
torch.zeros_like(input, dtype=None, layout=None, device=None, requires_grad=False)
## 依input形状创建全1张量
torch.ones_like(input, dtype=None, layout=None, device=None, requires_grad=False)
- input:创建与input形状相同的全0张量
- dtype:数据类型
- layout:内存中的布局形式
## 用法同上
torch.full(size, fill_value, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
torch.full_like(input, dtype=None, layout=torch.strided, device=None, requires_grad=False)
## 创建等差的张量,数值区间为[start, end)
torch.arange(start=0, end, step=1, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
## 创建均分的张量
torch.linspace(start, end, steps=100, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
- start: 数列起始值
- end: 数列“结束值”
- step: 数列公差,默认为1
- steps:数列长度
## 创建单位对角矩阵,默认为方阵
torch.eye(n, m=None, out=None, dtype=None, layout=torch.strided, device=None, requires_grad=False)
依据概率分布创建张量
## 生成正态分布
torch.normal(mean, std, out=None)
张量的操作
神经网络
随机梯度下降算法(SGD)
g
t
=
∇
θ
t
−
1
f
(
θ
t
−
1
)
∇
θ
t
=
−
η
∗
g
t
g_t = \nabla_{\theta_{t-1}}f(\theta_{t-1}) \\ \nabla_{\theta_{t}} = -\eta *g_t
gt=∇θt−1f(θt−1)∇θt=−η∗gt
g
t
g_t
gt是第
t
t
t步的梯度,
η
\eta
η是学习率(调整梯度影响大小的参数,一定程度上可以控制网络训练速度)
缺点
- 学习率 η \eta η难以确定合适的值
- 容易收敛到局部最优解
引入动量进行改进
g t = ∇ θ t − 1 f ( θ t − 1 ) m t = μ ∗ m t − 1 + g t ∇ θ t = − η ∗ m t g_t = \nabla_{\theta_{t-1}}f(\theta_{t-1}) \\ m_t = \mu*m_{t-1} + g_t \\ \nabla_{\theta_{t}} = -\eta *m_t gt=∇θt−1f(θt−1)mt=μ∗mt−1+gt∇θt=−η∗mt
m t m_t mt为当前动量的累加, μ \mu μ属于动量因子,用于调整上一步动量对参数更新时的重要程度。
Nesterov动量改进
g
t
=
∇
θ
t
−
1
f
(
θ
t
−
1
−
η
∗
μ
∗
m
t
−
1
)
m
t
=
μ
∗
m
t
−
1
+
g
t
∇
θ
t
=
−
η
∗
m
t
g_t = \nabla_{\theta_{t-1}}f(\theta_{t-1}-\eta*\mu*m_{t-1}) \\ m_t = \mu*m_{t-1} + g_t \\ \nabla_{\theta_{t}} = -\eta *m_t
gt=∇θt−1f(θt−1−η∗μ∗mt−1)mt=μ∗mt−1+gt∇θt=−η∗mt
计算施加当前速度之后的梯度,可看作在标准动量后添加一个校正因子。
PyTorch优化器
optim模块提供了多种内置优化算法,Adam类使用方式如下:
t
o
r
c
h
.
o
p
t
i
m
.
A
d
a
m
(
p
a
r
a
m
s
,
l
r
=
0.001
,
b
e
t
a
s
=
(
0.9
,
0.999
)
,
e
p
s
=
1
e
−
08
,
w
e
i
g
h
t
d
e
c
a
y
=
0
)
torch.optim.Adam(params, lr=0.001, betas=(0.9, 0.999), eps=1e-08,weight_decay=0)
torch.optim.Adam(params,lr=0.001,betas=(0.9,0.999),eps=1e−08,weightdecay=0)
- params:待优化参数的itrable、定义了参数组的dict。通常为model.parameters( )
- lr:算法学习率,默认为0.001
- betas:计算梯度以及梯度平方的运行平均值的系数
- eps:加到分母的项,增加数值计算的稳定性
- weight_decay:权重惩罚
定义优化器:
## 方式1 使用统一的学习率
optimizer = Adam(testnet.parameters(), lr = 0.001)
## 方式2 为不同的层定义不同的学习率
optimizer = Adam(
[{"params": testnet.hidden.parameters(),"lr":0.0001},
{"params":testnet.regression.parameters(),"lr":0.01}],
## 1e-2作用于其他没有指定的所有参数
lr = 1e-2)
损失函数
类 | 算法名称 |
---|---|
torch.nn.L1Loss( ) | 平均绝对值误差损失 |
torch.nn.MSELoss( ) | 均方误差损失 |
torch.nn.CrossEntropyLoss( ) | 交叉熵损失 |
torch.nn.MSELoss(size_average=None, reduce=None, reduction='mean')
- size_average:默认True,计算的损失为每个batch的均值,否则为每个batch的和
- reduce:默认为True
- reduction:取值为none、mean、sum
防止过拟合
- 增加数据量
- 合理的数据切分
- 正则化
- Dropout
- 提前结束训练