[深度学习实战]基于PyTorch的深度学习实战(上)[变量、求导、损失函数、优化器](二)

简介: 笔记

五、损失函数


  损失函数,又叫目标函数,是编译一个神经网络模型必须的两个参数之一。另一个必不可少的参数是优化器。

  损失函数是指用于计算标签值和预测值之间差异的函数,在机器学习过程中,有多种损失函数可供选择,典型的有距离向量,绝对值向量等

14.png

上图是一个用来模拟线性方程自动学习的示意图。粗线是真实的线性方程,虚线是迭代过程的示意,w1 是第一次迭代的权重,w2 是第二次迭代的权重,w3 是第三次迭代的权重。随着迭代次数的增加,我们的目标是使得 wn 无限接近真实值。

 那么怎么让 w 无限接近真实值呢?其实这就是损失函数和优化器的作用了。图中 1/2/3 这三个标签分别是 3 次迭代过程中预测 Y 值和真实 Y 值之间的差值(这里差值就是损失函数的意思了,当然了,实际应用中存在多种差值计算的公式),这里的差值示意图上是用绝对差来表示的,那么在多维空间时还有平方差,均方差等多种不同的距离计算公式,也就是损失函数了。

 这里示意的是一维度方程的情况,扩展到多维度,就是深度学习的本质了。

 下面介绍几种常见的损失函数的计算方法,pytorch 中定义了很多类型的预定义损失函数,需要用到的时候再学习其公式也不迟。

 我们先定义两个二维数组,然后用不同的损失函数计算其损失值。

15.png

import torch
from torch.autograd import Variable
import torch.nn as nn
import torch.nn.functional as F
sample = Variable(torch.ones(2,2))
a=torch.Tensor(2,2)
a[0,0]=0
a[0,1]=1
a[1,0]=2
a[1,1]=3
target = Variable (a)

sample 的值为:[[1,1],[1,1]]。

  target 的值为:[[0,1],[2,3]]。

5.1 nn.L1Loss

16.png

L1Loss 计算方法很简单,取预测值和真实值的绝对误差的平均数即可

criterion = nn.L1Loss()
loss = criterion(sample, target)
print(loss)

17.png

最后的结果为1,计算步骤为:

 先计算绝对差总和:|0-1|+|1-1|+|2-1|+|3-1|=4;

 然后再平均:4/4=1。


5.2 nn.SmoothL1Loss

 SmoothL1Loss 也叫作 Huber Loss,误差在 (-1,1) 上是平方损失,其他情况是 L1 损失。

18.png

criterion = nn.SmoothL1Loss()
loss = criterion(sample, target)
print(loss)

19.png

最后结果是:0.625。

5.3 nn.MSELoss

  平方损失函数。其计算公式是预测值和真实值之间的平方和的平均数

20.png

criterion = nn.MSELoss()
loss = criterion(sample, target)
print(loss)

21.png

 最后结果是:1.5。

5.4 nn.BCELoss

  二分类用的交叉熵,其计算公式较复杂,这里主要是有个概念即可,一般情况下不会用到。

22.png

 最后结果是:-50。

23.png

5.5 nn.CrossEntropyLoss

  交叉熵损失函数

24.png

该公式用的也较多,比如在图像分类神经网络模型中就常常用到该公式

criterion = nn.CrossEntropyLoss()
loss = criterion(sample, target)
print(loss)

25.png

最后结果是:2.0794。

 看文档我们知道 nn.CrossEntropyLoss 损失函数是用于图像识别验证的,对输入参数有各式要求,这里有这个概念就可以了,在后续的图像识别方向中会有正确的使用方法。


5.6 nn.NLLLoss

 负对数似然损失函数(Negative Log Likelihood)

26.png


在前面接上一个 LogSoftMax 层就等价于交叉熵损失了。注意这里的xlabel 和上个交叉熵损失里的不一样,这里是经过 log 运算后的数值。

 这个损失函数一般也是用在图像识别模型上。

criterion = F.nll_loss()
loss = criterion(sample, target)
print(loss)
loss=F.nll_loss(sample,target)

最后结果为报错,看来不能直接调用。

 Nn.NLLLoss 和 nn.CrossEntropyLoss 的功能是非常相似的。通常都是用在多分类模型中,实际应用中我们一般用 NLLLoss 比较多。

27.png

5.7 nn.NLLLoss2d

  和上面类似,但是多了几个维度,一般用在图片上。

input, (N, C, H, W)
target, (N, H, W)

  比如用全卷积网络做分类时,最后图片的每个点都会预测一个类别标签

28.png

最后结果报错,看来不能直接这么用。


六、优化器Optim


 优化器用通俗的话来说就是一种算法,是一种计算导数的算法。

 各种优化器的目的和发明它们的初衷其实就是能让用户选择一种适合自己场景的优化器。

 优化器的最主要的衡量指标就是优化曲线的平稳度,最好的优化器就是每一轮样本数据的优化都让权重参数匀速的接近目标值,而不是忽上忽下跳跃的变化。因此损失值的平稳下降对于一个深度学习模型来说是一个非常重要的衡量指标。

 pytorch 的优化器都放在 torch.optim 包中。常见的优化器有:SGD,Adam,Adadelta,Adagrad,Adamax 等。如果需要定制特殊的优化器,pytorch 也提供了定制化的手段,不过这里我们就不去深究了,毕竟预留的优化器的功能已经足够强大了。


 6.1 SGD

 SGD 指stochastic gradient descent,即随机梯度下降,随机的意思是随机选取部分数据集参与计算,是梯度下降的 batch 版本。SGD 支持动量参数,支持学习衰减率。SGD 优化器也是最常见的一种优化器,实现简单,容易理解。


 6.1.1 用法

optimizer = optim.SGD(model.parameters(), lr = 0.01, momentum=0.9)


 6.1.2 参数

 lr:大于 0 的浮点数,学习率。

 momentum:大于 0 的浮点数,动量参数。

 parameters:Variable 参数,要优化的对象。


 对于训练数据集,我们首先将其分成 n 个 batch,每个 batch 包含 m 个样本。我们每次更新都利用一个 batch 的数据 ,而非整个训练集,即:


 xt+1=xt+Δxt

 Δxt=-ηgt


 其中,η 为学习率,gt 为 x 在 t 时刻的梯度。


 6.1.3 好处

 这么做的好处在于:

 (1)当训练数据太多时,利用整个数据集更新往往时间上不现实。batch的方法可以减少机器的压力,并且可以更快地收敛。

 (2)当训练集有很多冗余时(类似的样本出现多次),batch 方法收敛更快。以一个极端情况为例,若训练集前一半和后一半梯度相同,那么如果前一半作为一个 batch,后一半作为另一个 batch,那么在一次遍历训练集时,batch 的方法向最优解前进两个 step,而整体的方法只前进一个 step。


6.2 RMSprop

 RMSProp 通过引入一个衰减系数,让 r 每回合都衰减一定比例,类似于Momentum 中的做法,该优化器通常是面对递归神经网络时的一个良好选择。


 6.2.1 具体实现

 需要:全局学习速率 ϵ,初始参数 θ,数值稳定量 δ,衰减速率 ρ。

 中间变量:梯度累计量 r(初始化为 0)。


 6.2.2 每步迭代过程

 (1)从训练集中的随机抽取一批容量为 m 的样本 {x1,…,xm} 以及相关的输出 yi 。

 (2)计算梯度和误差,更新 r,再根据 r 和梯度计算参数更新量 。


29.png

6.2.3 用法

keras.optimizers.RMSprop(lr=0.001, rho=0.9, epsilon=1e-06)


 6.2.4 参数

 lr:大于 0 的浮点数,学习率。

 rho:大于 0 的浮点数。

 epsilon:大于 0 的小浮点数,防止除 0 错误。


6.3 Adagrad

 AdaGrad 可以自动变更学习速率,只是需要设定一个全局的学习速率 ϵ,但是这并非是实际学习速率,实际的速率是与以往参数的模之和的开方成反比的。也许说起来有点绕口,不过用公式来表示就直白的多:

30.png

其中 δ 是一个很小的常量,大概在 10-7,防止出现除以 0 的情况.。


 6.3.1 具体实现

 需要:全局学习速率 ϵ,初始参数 θ,数值稳定量 δ 。

 中间变量:梯度累计量 r(初始化为 0) 。


 6.3.2 每步迭代过程

 (1) 从训练集中的随机抽取一批容量为 m 的样本 {x1,…,xm} 以及相关。

 (2)计算梯度和误差,更新r,再根据 r 和梯度计算参数更新量 。

31.png

6.3.3 优点

 能够实现学习率的自动更改。如果这次梯度大,那么学习速率衰减的就快一些;如果这次梯度小,那么学习速率衰减的就慢一些。


 6.3.4 缺点

 仍然要设置一个变量 ϵ 。

 经验表明,在普通算法中也许效果不错,但在深度学习中,深度过深时会造成训练提前结束。


 6.3.5 用法

keras.optimizers.Adagrad(lr=0.01, epsilon=1e-06)


 6.3.6 参数

 lr:大于 0 的浮点数,学习率。

 epsilon:大于 0 的小浮点数,防止除 0 错误。


6.4 Adadelta

 Adagrad 算法存在三个问题:

 (1)其学习率是单调递减的,训练后期学习率非常小。

 (2)其需要手工设置一个全局的初始学习率。

 (3)更新 xt 时,左右两边的单位不统一。

 Adadelta 针对上述三个问题提出了比较漂亮的解决方案。

 首先,针对第一个问题,我们可以只使用 adagrad 的分母中的累计项离当前时间点比较近的项,如下式:


32.png

这里ρ 是衰减系数 ,通过这个衰减系数,我们令每一个时刻的 gt 随时间按照 ρ 指数衰减,这样就相当于我们仅使用离当前时刻比较近的gt信息,从而使得还很长时间之后,参数仍然可以得到更新。

 针对第三个问题,其实 sgd 跟 momentum 系列的方法也有单位不统一的问题。sgd、momentum 系列方法中:

33.png

 类似的,adagrad 中,用于更新 Δx 的单位也不是 x 的单位,而是 1

  而对于牛顿迭代法

34.png

 其中 H 为 Hessian 矩阵,由于其计算量巨大,因而实际中不常使用。其单位为:

35.png

注意,这里f 无单位 。因而,牛顿迭代法的单位是正确的

  所以,我们可以模拟牛顿迭代法来得到正确的单位。注意到:

36.png

这里,在解决学习率单调递减的问题的方案中,分母已经是 ∂f/∂x 的一个近似了。这里我们可以构造 Δx 的近似,来模拟得到 H-1 的近似从而得到近似的牛顿迭代法。具体做法如下:

37.png

可以看到,如此一来adagrad 中分子部分需要人工设置的初始学习率也消失了 ,从而顺带解决了上述的第二个问题。


 6.4.1 用法

keras.optimizers.Adadelta(lr=1.0, rho=0.95, epsilon=1e-06)


建议保持优化器的默认参数不变。


 6.4.2 参数

 lr:大于 0 的浮点数,学习率。

 rho:大于 0 的浮点数。

 epsilon:大于 0 的小浮点数,防止除 0 错误。


6.5 Adam

 Adam 是一种基于一阶梯度来优化随机目标函数的算法。

 Adam 这个名字来源于 adaptive moment estimation,自适应矩估计。概率论中矩的含义是:如果一个随机变量 X 服从某个分布,X 的一阶矩是E(X),也就是样本平均值,X 的二阶矩就是 E(X^2),也就是样本平方的平均值。

 Adam 算法根据损失函数对每个参数的梯度的一阶矩估计和二阶矩估计动态调整针对于每个参数的学习速率。Adam 也是基于梯度下降的方法,但是每次迭代参数的学习步长都有一个确定的范围,不会因为很大的梯度导致很大的学习步长,参数的值比较稳定。

 Adam(Adaptive Moment Estimation)本质上是带有动量项的 RMSprop,它利用梯度的一阶矩估计和二阶矩估计动态调整每个参数的学习率。Adam 的优点主要在于经过偏置校正后,每一次迭代学习率都有个确定范围,使得参数比较平稳。


6.5.1 具体实现

 需要:步进值 ϵ,初始参数 θ,数值稳定量 δ,一阶动量衰减系数 ρ1,二阶动量衰减系数 ρ2 。

 其中几个取值一般为:δ=10-8,ρ1=0.9,ρ2=0.999 。

 中间变量:一阶动量 s,二阶动量 r,都初始化为 0 。


6.5.2 每步迭代过程

 (1)从训练集中的随机抽取一批容量为 m 的样本 {x1,…,xm} 以及相关的输出 yi 。

 (2)计算梯度和误差,更新 r 和 s,再根据 r 和 s 以及梯度计算参数更新量 。


38.png

6.5.3 用法

keras.optimizers.Adam(lr=0.001, beta_1=0.9, beta_2=0.999, epsilon=1e-08)


 6.5.4 参数

 lr:大于 0 的浮点数,学习率。

 beta_1/beta_2:浮点数, 0<beta<1,通常很接近 1。

 epsilon:大于 0 的小浮点数,防止除0错误。


6.6 Adamax

keras.optimizers.Adamax(lr=0.002, beta_1=0.9, beta_2=0.999, epsilon=1e-08)

 Adamax 优化器的方法是基于无穷范数的 Adam 方法的变体。


 6.6.1 参数

 lr:大于 0 的浮点数,学习率。

 beta_1/beta_2:浮点数, 0<beta<1,通常很接近 1。

 epsilon:大于 0 的小浮点数,防止除 0 错误。


相关文章
|
1月前
|
机器学习/深度学习 算法 开发者
探索深度学习中的优化器选择对模型性能的影响
在深度学习领域,优化器的选择对于模型训练的效果具有决定性作用。本文通过对比分析不同优化器的工作原理及其在实际应用中的表现,探讨了如何根据具体任务选择合适的优化器以提高模型性能。文章首先概述了几种常见的优化算法,包括梯度下降法、随机梯度下降法(SGD)、动量法、AdaGrad、RMSProp和Adam等;然后,通过实验验证了这些优化器在不同数据集上训练神经网络时的效率与准确性差异;最后,提出了一些基于经验的规则帮助开发者更好地做出选择。
|
1月前
|
机器学习/深度学习 监控 PyTorch
深度学习工程实践:PyTorch Lightning与Ignite框架的技术特性对比分析
在深度学习框架的选择上,PyTorch Lightning和Ignite代表了两种不同的技术路线。本文将从技术实现的角度,深入分析这两个框架在实际应用中的差异,为开发者提供客观的技术参考。
49 7
|
2月前
|
机器学习/深度学习 算法 PyTorch
深度学习笔记(十三):IOU、GIOU、DIOU、CIOU、EIOU、Focal EIOU、alpha IOU、SIOU、WIOU损失函数分析及Pytorch实现
这篇文章详细介绍了多种用于目标检测任务中的边界框回归损失函数,包括IOU、GIOU、DIOU、CIOU、EIOU、Focal EIOU、alpha IOU、SIOU和WIOU,并提供了它们的Pytorch实现代码。
327 1
深度学习笔记(十三):IOU、GIOU、DIOU、CIOU、EIOU、Focal EIOU、alpha IOU、SIOU、WIOU损失函数分析及Pytorch实现
|
3月前
|
机器学习/深度学习 PyTorch 调度
在Pytorch中为不同层设置不同学习率来提升性能,优化深度学习模型
在深度学习中,学习率作为关键超参数对模型收敛速度和性能至关重要。传统方法采用统一学习率,但研究表明为不同层设置差异化学习率能显著提升性能。本文探讨了这一策略的理论基础及PyTorch实现方法,包括模型定义、参数分组、优化器配置及训练流程。通过示例展示了如何为ResNet18设置不同层的学习率,并介绍了渐进式解冻和层适应学习率等高级技巧,帮助研究者更好地优化模型训练。
207 4
在Pytorch中为不同层设置不同学习率来提升性能,优化深度学习模型
|
2月前
|
机器学习/深度学习 算法 数据可视化
如果你的PyTorch优化器效果欠佳,试试这4种深度学习中的高级优化技术吧
在深度学习领域,优化器的选择对模型性能至关重要。尽管PyTorch中的标准优化器如SGD、Adam和AdamW被广泛应用,但在某些复杂优化问题中,这些方法未必是最优选择。本文介绍了四种高级优化技术:序列最小二乘规划(SLSQP)、粒子群优化(PSO)、协方差矩阵自适应进化策略(CMA-ES)和模拟退火(SA)。这些方法具备无梯度优化、仅需前向传播及全局优化能力等优点,尤其适合非可微操作和参数数量较少的情况。通过实验对比发现,对于特定问题,非传统优化方法可能比标准梯度下降算法表现更好。文章详细描述了这些优化技术的实现过程及结果分析,并提出了未来的研究方向。
37 1
|
3月前
|
机器学习/深度学习 数据挖掘 PyTorch
🎓PyTorch深度学习入门课:编程小白也能玩转的高级数据分析术
踏入深度学习领域,即使是编程新手也能借助PyTorch这一强大工具,轻松解锁高级数据分析。PyTorch以简洁的API、动态计算图及灵活性著称,成为众多学者与工程师的首选。本文将带你从零开始,通过环境搭建、构建基础神经网络到进阶数据分析应用,逐步掌握PyTorch的核心技能。从安装配置到编写简单张量运算,再到实现神经网络模型,最后应用于图像分类等复杂任务,每个环节都配有示例代码,助你快速上手。实践出真知,不断尝试和调试将使你更深入地理解这些概念,开启深度学习之旅。
48 1
|
3月前
|
机器学习/深度学习
小土堆-pytorch-神经网络-损失函数与反向传播_笔记
在使用损失函数时,关键在于匹配输入和输出形状。例如,在L1Loss中,输入形状中的N代表批量大小。以下是具体示例:对于相同形状的输入和目标张量,L1Loss默认计算差值并求平均;此外,均方误差(MSE)也是常用损失函数。实战中,损失函数用于计算模型输出与真实标签间的差距,并通过反向传播更新模型参数。
|
2月前
|
机器学习/深度学习 数据采集 自然语言处理
【NLP自然语言处理】基于PyTorch深度学习框架构建RNN经典案例:构建人名分类器
【NLP自然语言处理】基于PyTorch深度学习框架构建RNN经典案例:构建人名分类器
|
3月前
|
机器学习/深度学习 自动驾驶 搜索推荐
深度学习之探索神经网络、感知器与损失函数
在当今的数字化时代,深度学习作为一种强大的机器学习技术,正在迅速改变着我们的生活方式。无论是智能推荐系统、自动驾驶车辆还是语音识别应用,深度学习都在背后默默地发挥作用。
61 1
|
3月前
|
机器学习/深度学习 数据挖掘 TensorFlow
解锁Python数据分析新技能,TensorFlow&PyTorch双引擎驱动深度学习实战盛宴
在数据驱动时代,Python凭借简洁的语法和强大的库支持,成为数据分析与机器学习的首选语言。Pandas和NumPy是Python数据分析的基础,前者提供高效的数据处理工具,后者则支持科学计算。TensorFlow与PyTorch作为深度学习领域的两大框架,助力数据科学家构建复杂神经网络,挖掘数据深层价值。通过Python打下的坚实基础,结合TensorFlow和PyTorch的强大功能,我们能在数据科学领域探索无限可能,解决复杂问题并推动科研进步。
71 0