您的位置:首页 > 财经 > 产业 > 工业设计公司排行_机械设备公司网站制作_西安全网优化_爱站网挖掘词

工业设计公司排行_机械设备公司网站制作_西安全网优化_爱站网挖掘词

2025/4/19 0:05:59 来源:https://blog.csdn.net/m0_61360701/article/details/147011748  浏览:    关键词:工业设计公司排行_机械设备公司网站制作_西安全网优化_爱站网挖掘词
工业设计公司排行_机械设备公司网站制作_西安全网优化_爱站网挖掘词

《动手学深度学习》-4.8-笔记

“数值的稳定性”?

就是你写的代码不会因为数太大/太小,而导致 计算错误、NaN、inf、崩溃或精度爆炸

假设有个操作是:

torch.exp(1000) # 计算 e^1000

这个结果太大太大,超出 float32 能表达的范围了

“数值不稳定”的情况:

场景问题
exp() 输入太大变成 inf
log(0)是负无穷,变成 -inf
softmax 后再 log如果某类概率为 0 → log(0) = -inf
梯度更新太大loss → NaN,模型权重爆炸
float32 精度不够小数相减、乘除等 → 精度丢失

 

如何防止数值不稳定?

方法说明
使用 log_softmax 替代 softmaxPyTorch 提供的版本更稳定
使用 torch.clamp() 限值限制数据在某个范围内防止爆炸
加上一个小常数 epsilonlog(x + 1e-8) 避免 log(0)
梯度裁剪 clip_grad_norm_限制梯度太大
float64(高精度)如果 float32 太不稳,可以换成 float64
使用稳定的优化器(如 Adam)相比 SGD,Adam 对浮动更稳

神经网络变得很深时 ,数值极其容易不稳定

在深度学习里,梯度(gradient) 就是一个向量,告诉我们:“当前参数往哪个方向、改多少,能让 loss 更小。”

可以理解为:梯度 = 导数 = 变化率 = “朝哪个方向爬坡/下坡”。

举一个例子

你现在在山坡上(就是一个 loss 值),你想走到山谷最低点(就是让 loss 趋近于 0),
你怎么走呢?
 你得知道往哪个方向走“会变低”,这就叫“梯度方向”。

神经网络训练过程其实就是:
不断往“loss 越小”的方向调整参数。

神经网络中梯度的作用:

名称说明
梯度(Gradient)是 loss 对模型参数的偏导数,表示如何改变参数以减小 loss
用途在反向传播中用来更新每个参数
关键操作.backward() 会自动帮你计算所有梯度(自动微分)

梯度消失(Vanishing Gradients)

梯度消失是指在反向传播过程中,随着层数的增加,梯度值变得越来越小,最终趋近于零,导致网络的更新变得极其缓慢,甚至完全停止更新。

  • 原因:常见的激活函数 Sigmoid 会导致梯度消失问题。Sigmoid 函数的输出在极大或极小的输入值下会趋近于 0,而其梯度也会趋近于 0。在深层网络中,反向传播时的梯度值经过每一层的乘积后会迅速变小,导致梯度消失。

  • 解决方法:使用 ReLU(Rectified Linear Unit)系列激活函数。ReLU 函数在大多数情况下不会导致梯度消失,能够有效地避免梯度在传播过程中衰减过快。ReLU 和其变体(如 Leaky ReLU、ELU)成为了深度网络的默认选择。

梯度爆炸(Exploding Gradients)

梯度爆炸则是与梯度消失相对的现象。当网络中权重值过大时,反向传播时计算出来的梯度会变得极其巨大,导致权重更新过大,模型的训练变得不稳定。

  • 原因:当网络层数很多,且每层的权重初始化较大时,矩阵的乘积可能会迅速变大,导致梯度爆炸。特别是在深度神经网络中,梯度可能通过多个层级放大,导致更新过大。

  • 解决方法:采用合适的 权重初始化方法,如 Xavier 初始化He 初始化,以及 梯度裁剪(Gradient Clipping) 技术,来防止梯度的值变得过大。

梯度相关的常见问题:

问题说明或解决办法
梯度消失(vanishing)梯度变成0,导致网络学不到东西
梯度爆炸(exploding)梯度太大,模型发散,loss变成NaN
没有 .backward()不会计算梯度
梯度没有清零 .zero_grad()每次训练后要手动清零梯度,不然会累加

权重初始化(Weight Initialization) 是深度学习中一个非常重要的技术,它决定了神经网络中每个神经元的初始权重值。合理的权重初始化可以加速网络的收敛过程,避免梯度消失或梯度爆炸等问题。下面,我会详细解释权重初始化的概念以及常见的几种方法。

常见的权重初始化方法:

  1. 零初始化(Zero Initialization)

    • 将所有的权重初始化为 0。虽然实现简单,但会导致网络的学习停滞,因为所有神经元的输出会相同,无法打破对称性,因此这种方法通常不使用。

  2. 随机初始化(Random Initialization)

    • 通过随机生成小的权重值来初始化网络中的权重。常见的初始化方法有:

    • 均匀分布初始化(Uniform Initialization)
      将权重初始化为一个均匀分布的随机值,通常是从 [-1, 1] 或 [-0.1, 0.1] 的范围内随机抽取。

    • 正态分布初始化(Normal Initialization)
      从一个标准正态分布中随机抽取权重,均值为 0,标准差为某个小值。例如:

      nn.init.normal_(m.weight, mean=0.0, std=0.01)

      这种方法适用于许多神经网络。

  3. Xavier 初始化(Xavier Initialization,也叫 Glorot Initialization)

    • 这个方法特别适用于 SigmoidTanh 激活函数的网络。

    • 通过根据前一层和当前层的神经元数量来初始化权重。具体来说,它会将权重初始化为一个均匀分布或正态分布,其方差是根据输入和输出的大小自动计算的,旨在保持每层输入和输出的方差一致。

    • 公式

      • 均匀分布初始化:

      • 其中,n_inn_out 分别是前一层和当前层神经元的数量。

  4. He 初始化(He Initialization)

    • 这个方法专门设计用于 ReLU 激活函数的网络。由于 ReLU 激活函数对负值输出为零,可能导致神经元的输出较小,使用 He 初始化 可以避免梯度消失。

    • 公式

      • 均匀分布初始化:

      • 正态分布初始化:

      • 其中,n_in 是当前层的输入神经元数量。

  5. LeCun 初始化

    • 这个初始化方法是为 Leaky ReLUSigmoid 激活函数设计的,它通过利用输入层的神经元数量来决定权重的标准差,从而确保训练过程中梯度的稳定性。

    • 公式

总结:

  1. 梯度消失和梯度爆炸 都是由于网络的权重初始化不当或者激活函数选择不合适导致的。合理的初始化方法能够缓解这两个问题。

  2. Xavier 初始化 是一种常用的初始化方法,它考虑了网络层的输入和输出尺寸,从而避免了梯度消失和爆炸问题。

  3. 使用 ReLU 激活函数通常能够避免梯度消失的问题,因此在大多数深度网络中,ReLU 被广泛使用。

%matplotlib inline  # 在 Jupyter 或 Colab 环境中直接在笔记本中显示图形,而不是弹出新窗口
import torch  # 导入 PyTorch 库,用于张量计算和深度学习模型的构建
from d2l import torch as d2l  # 导入 d2l 库,它提供了一些便捷的工具用于绘图等操作x = torch.arange(-8.0, 8.0, 0.1, requires_grad=True)  # 创建一个包含从 -8.0 到 8.0(步长为 0.1)的张量 x,并且设置 requires_grad=True 以便后续计算梯度
y = torch.sigmoid(x)  # 计算 x 上的 Sigmoid 激活函数,Sigmoid(x) = 1 / (1 + exp(-x))
y.backward(torch.ones_like(x))  # 进行反向传播,计算 y 相对于 x 的梯度,torch.ones_like(x) 传递梯度的大小为 1(即对每个元素都计算梯度)# 绘制图形,使用 d2l.plot 函数来展示 Sigmoid 函数的输出和其梯度
# x.detach().numpy():将张量 x 从计算图中分离出来,转为 NumPy 数组,用于绘图
# y.detach().numpy():将 Sigmoid 函数的输出 y 从计算图中分离出来,转为 NumPy 数组
# x.grad.numpy():获取张量 x 的梯度,并转为 NumPy 数组
# legend=['sigmoid', 'gradient']:设置图例,分别标注 Sigmoid 曲线和梯度曲线
# figsize=(4.5, 2.5):设置图形的大小
d2l.plot(x.detach().numpy(), [y.detach().numpy(), x.grad.numpy()],legend=['sigmoid', 'gradient'], figsize=(4.5, 2.5))

图像分析

  • Sigmoid 曲线:显示了 Sigmoid 激活函数在不同输入值(x)下的输出(y)。它的输出范围是 (0, 1),输入值越大,输出越接近 1,输入值越小,输出越接近 0。

  • Sigmoid 函数的梯度:显示了 Sigmoid 函数的导数(梯度)。当 x 接近 0 时,梯度值最大;而当 x 变得非常大或非常小时,梯度会迅速变小,接近于零。这正是 梯度消失 问题的根源之一。

1. NaN (Not a Number)

NaN 代表 "不是一个数",通常表示计算结果无法定义或不合法。常见的原因包括:

  • 0 除以 0:在数学中,0 除以 0 是没有意义的操作,因此会产生 NaN。这是一种不确定的运算,不能给出一个明确的结果。

  • 负数的平方根:在实数范围内,负数没有平方根。例如,sqrt(-1) 在实数域中是没有定义的,因此会产生 NaN

  • 对零取对数:数学上,log(0) 是没有定义的,因为对数函数在零处没有意义,所以会返回 NaN

  • Inf 减去 Inf:当两个无穷大的数值相减时,其结果是无法确定的,因此会得到 NaN。例如,Inf - Inf 是不确定的。

  • 无效的数学操作:如 0 * InfInf / Inf 等操作,这些都是无法计算的,通常会产生 NaN

2. Inf (Infinity)

Inf 代表无穷大,通常表示数值超出了计算机表示范围的极限,或者表示某些数学操作的结果是无限大的。常见的原因包括:

  • 除以零:当你尝试进行除法运算,且除数为零,而被除数不为零时(例如,1/0),数学上这是一个无穷大的结果。正数除以零会产生正无穷大(+Inf),负数除以零会产生负无穷大(-Inf)。

  • 数值溢出:当一个运算结果超出了浮点数能表示的最大值时,就会返回 Inf。例如,某些运算(如指数增长)可能导致数值过大,无法表示,系统会将其标记为 Inf

  • 计算超出表示范围的结果:在某些计算中,当结果超过浮点数的最大表示值时(如极大指数的计算),就会变成 Inf。这种情况通常发生在计算极大的数值时,例如计算指数时(exp(x) 在 x 很大时会爆炸)。

  • 正无穷大与负无穷大的运算:当涉及到 Inf-Inf 的加法或减法时,结果可能是无穷大。正无穷加上一个大数仍然是正无穷,而负无穷加上一个负大数会得到负无穷。

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com