动手学深度学习11.9. Adadelta-笔记&练习(PyTorch)

以下内容为结合李沐老师的课程和教材补充的学习笔记,以及对课后练习的一些思考,自留回顾,也供同学之人交流参考。

本节课程地址:72 优化算法【动手学深度学习v2】_哔哩哔哩_bilibili

本节教材地址:11.9. Adadelta --- 动手学深度学习 2.0.0 documentation

本节开源代码:...>d2l-zh>pytorch>chapter_optimization>adadelta.ipynb


Adadelta

Adadelta是AdaGrad的另一种变体( 11.7节 ), 主要区别在于前者减少了学习率适应坐标的数量。 此外,广义上Adadelta被称为没有学习率,因为它使用变化量本身作为未来变化的校准。 Adadelta算法是在 (Zeiler, 2012)中提出的。

Adadelta算法

简而言之,Adadelta使用两个状态变量, 用于存储梯度二阶导数的泄露平均值, 用于存储模型本身中参数变化二阶导数的泄露平均值。请注意,为了与其他出版物和实现的兼容性,我们使用作者的原始符号和命名(没有其它真正理由让大家使用不同的希腊变量来表示在动量法、AdaGrad、RMSProp和Adadelta中用于相同用途的参数)。

以下是Adadelta的技术细节。鉴于参数du jour是 ,我们获得了与 11.8节 类似的以下泄漏更新:

11.8节 的区别在于,我们使用重新缩放的梯度 执行更新,即

那么,调整后的梯度 是什么?我们可以按如下方式计算它:

其中 Δxt−1 是重新缩放梯度的平方 的泄漏平均值。我们将 初始化为0,然后在每个步骤中使用 更新它,即

(例如 这样的小值)是为了保持数字稳定性而加入的。

代码实现

Adadelta需要为每个变量维护两个状态变量,即 。这将产生以下实现。

复制代码
%matplotlib inline
import torch
from d2l import torch as d2l


def init_adadelta_states(feature_dim):
    s_w, s_b = torch.zeros((feature_dim, 1)), torch.zeros(1)
    delta_w, delta_b = torch.zeros((feature_dim, 1)), torch.zeros(1)
    return ((s_w, delta_w), (s_b, delta_b))

def adadelta(params, states, hyperparams):
    rho, eps = hyperparams['rho'], 1e-5
    for p, (s, delta) in zip(params, states):
        with torch.no_grad():
            # In-place updates via [:] 原地更新,不会干扰计算图的结构
            s[:] = rho * s + (1 - rho) * torch.square(p.grad)
            g = (torch.sqrt(delta + eps) / torch.sqrt(s + eps)) * p.grad
            p[:] -= g
            delta[:] = rho * delta + (1 - rho) * g * g
        p.grad.data.zero_()

对于每次参数更新,选择 相当于10个半衰期。由此我们得到:

复制代码
data_iter, feature_dim = d2l.get_data_ch11(batch_size=10)
d2l.train_ch11(adadelta, init_adadelta_states(feature_dim),
               {'rho': 0.9}, data_iter, feature_dim)

输出结果:

loss: 0.244, 0.031 sec/epoch

为了简洁实现,我们只需使用高级API中的Adadelta算法。

复制代码
trainer = torch.optim.Adadelta
d2l.train_concise_ch11(trainer, {'rho': 0.9}, data_iter)

输出结果:

loss: 0.243, 0.011 sec/epoch

小结

  • Adadelta没有学习率参数。相反,它使用参数本身的变化率来调整学习率。
  • Adadelta需要两个状态变量来存储梯度的二阶导数和参数的变化。
  • Adadelta使用泄漏的平均值来保持对适当统计数据的运行估计。

练习

  1. 调整 的值,会发生什么?
    解:
    类似于RMSProp的 之于Adadelta也是一个介于 0 和 1 之间的值,用于平衡历史信息和当前信息的权重。
    接近于1时,模型会更多地依赖于过去的梯度和更新量信息;
    接近于0时,模型会更多地依赖于当前的梯度和更新量信息。

  2. 展示如何在不使用 的情况下实现算法。为什么这是个好主意?
    解:
    是一个显式的中间变量,不使用 ,即直接在更新变量时进行计算和累积量时进行计算,这样做可以减少内存占用,但实际计算量是重复的,所以每epoch的计算用时增加了。

    def adadelta_no_g(params, states, hyperparams):
    rho, eps = hyperparams['rho'], 1e-5
    for p, (s, delta) in zip(params, states):
    with torch.no_grad():
    s[:] = rho * s + (1 - rho) * p.grad ** 2
    p[:] -= (torch.sqrt(delta + eps) / torch.sqrt(s + eps)) * p.grad
    delta[:] = rho * delta + (1 - rho) * ((torch.sqrt(delta + eps) / torch.sqrt(s + eps)) * p.grad) ** 2
    p.grad.data.zero_()
    d2l.train_ch11(adadelta_no_g, init_adadelta_states(feature_dim),
    {'rho': 0.9}, data_iter, feature_dim)

输出结果:
loss: 0.243, 0.016 sec/epoch

  1. Adadelta真的是学习率为0吗?能找到Adadelta无法解决的优化问题吗?
    解:
    不是,Adadelta 是一种自适应学习率优化算法,它的学习率并不是固定的也不是为0,而是动态调整的,具体为:

Adadelta 在处理非凸优化问题时可能会遇到困难。非凸优化问题的损失函数可能有多个局部最小值,Adadelta 可能会陷入局部最小值而无法找到全局最小值。
在某些情况下,梯度可能非常稀疏,即大部分梯度值为零,这时,Adadelta 的累积梯度平方 st 可能会变得非常小,导致学习率变得非常大。这可能会导致参数更新过大,从而破坏训练过程。例如,在训练稀疏数据集(如某些自然语言处理任务)时,Adadelta 可能会表现不佳。

  1. 将Adadelta的收敛行为与AdaGrad和RMSProp进行比较。
    解:

| 算法 | AdaGrad | RMSProp | Adadelta |
| 收敛速度 | 在训练初期,AdaGrad 的收敛速度较快,因为它能够快速调整学习率以适应稀疏梯度。 | 在训练初期,RMSProp 的收敛速度相对较快,因为它能够更好地适应动态变化的梯度。 | 在训练初期,Adadelta 的收敛速度可能较慢,因为它依赖于历史信息来调整学习率。 |
| 后期表现 | 由于累积梯度平方不断增大,学习率逐渐减小,最终可能趋近于零,导致训练停止。 | 由于引入了衰减率 \\gamma,RMSProp 能够保持相对稳定的学习率,避免了学习率趋近于零的问题。 | Adadelta 能够自适应地调整学习率,避免了手动设置全局学习率的问题。 |

适用场景 适用于稀疏梯度问题,如自然语言处理中的词嵌入。 适用于非平稳优化问题,如深度神经网络的训练。 适用于非平稳优化问题,尤其是需要长期依赖历史信息的任务。
相关推荐
Fansv5871 小时前
深度学习框架PyTorch——从入门到精通(3)数据集和数据加载器
人工智能·pytorch·深度学习
吴梓穆2 小时前
UE4学习笔记 FPS游戏制作10 制作UI准星
笔记·学习·ue4
nuc-1272 小时前
sqli-labs学习笔记3
数据库·笔记·学习·sqli-labs
狄加山6755 小时前
QT 学习笔记2
笔记·qt·学习
一面千人5 小时前
从零开始:基于 PyTorch 的图像分类模型
pytorch·深度学习·cnn·图像分类·模型优化·cifar-10·调试经验·前沿趋势
墨绿色的摆渡人5 小时前
pytorch小记(十二):pytorch中 masked_fill_() vs. masked_fill() 详解
人工智能·pytorch·python
迷鹿鹿鹿鹿鹿5 小时前
【基于深度学习的验证码识别】---- part3数据加载、模型等API介绍(1)
人工智能·pytorch·爬虫·深度学习
天师电通电容爆破工程师6 小时前
Altium Design元件管理笔记
笔记
Kai HVZ7 小时前
《深度学习》——YOLOv2详解
人工智能·深度学习·yolo