深度学习中的一些概念解释



一、正向传播和反向传播


  • 在模型训练过程中,是同时包含正向传播和反向传播的

    • 正向传播是模型根据输入数据和当前的参数(权重和偏置)计算预测输出的过程。例如,在一个图像分类神经网络模型中,输入是图像的像素数据,经过多个隐藏层的计算,最终在输出层得到预测的类别概率分布。

    • 反向传播紧接着正向传播进行。它基于正向传播得到的预测输出和真实标签之间的差异(通过损失函数来衡量),计算每个参数的梯度。这个梯度表示了参数对损失函数的影响程度,然后利用这些梯度来更新模型的参数(权重和偏置)。

    • 这种正向传播和反向传播的交替进行是模型训练的核心机制。每次正向传播得到预测结果后,通过反向传播调整参数,然后再进行下一次正向传播,如此反复,直到模型收敛(即损失函数的值不再显著下降或者达到预设的训练轮数等停止条件)。


  • 在多层神经网络中,即使中间层没有像输出层那样的真实标签,依然可以进行反向传播。

    • 在反向传播阶段,中间层的参数更新是基于损失函数对输出层的影响,通过链式法则将误差从输出层反向传播回中间层来间接利用损失函数,以此来更新中间层的参数,使网络整体朝着损失减小的方向优化。




二、梯度消失 梯度爆炸



梯度的概念:


  • 梯度消失时,靠近输入层的网络层的参数更新变得非常缓慢。因为参数更新是通过梯度乘以学习率来实现的,梯度接近于零会导致这些层的参数几乎无法更新,使得模型难以学习到输入数据的有效特征,从而导致训练过程漫长,甚至无法收敛到一个较好的结果

  • 梯度爆炸会使模型的训练过程变得极不稳定。参数更新步长过大可能会导致模型在训练过程中跳过最优解,甚至无法收敛。


梯度爆炸的可能原因:

  1. 深度过深的神经网络

    • 当神经网络的层数非常多时,梯度在反向传播过程中要经过很多层。例如,在一个非常深的递归神经网络(RNN)中,假设每一层的梯度都大于1,那么经过多层的反向传播,梯度就会呈指数级增长。
    • 以简单的全连接神经网络为例,如果有100层,每层的梯度放大因子为1.5(这是一个假设的大于1的值),那么从最后一层反向传播到第一层时,梯度就会变为,这是一个非常大的值。这种情况在深度神经网络如Transformer架构出现之前的一些极深的网络结构中很容易出现。
  2. 循环神经网络中的长序列问题(针对RNN)

    • 在循环神经网络中,处理长序列数据时,梯度会随着时间步的反向传播而累积。对于像长文本生成等任务,时间步可能会很长。
    • 假设一个RNN在处理一个包含1000个时间步的序列,在反向传播过程中,每个时间步的梯度都有可能被放大。因为RNN的梯度计算涉及到时间步的连乘,即,其中ht是时间步t的隐藏状态。如果这个连乘过程中的某些项大于1,随着时间步的增加,梯度就会爆炸。
  3. 过大的权重初始化

    • 如果神经网络的权重初始化值过大,那么在正向传播时,输出值可能会变得很大。在反向传播计算梯度时,根据链式法则,梯度会和权重等参数相关。
    • 例如,在一个简单的线性层y = Wx + b,其中W是权重矩阵,x是输入向量。损失函数为,对W求梯度。如果W初始值过大,使得y很大,那么梯度也可能会很大。常见的均匀分布或正态分布初始化方法,如果参数范围设置不合理(例如,正态分布的标准差设置得过大),就可能导致这种情况。
  4. 不恰当的激活函数及其导数性质

    • 某些激活函数的导数可能会导致梯度爆炸。例如,Sigmoid函数,其导数为,当输入值的绝对值较大时,导数趋近于0。但是在某些情况下,如果网络的输出使得激活函数的输入处于导数较大的区域,并且在反向传播过程中,这些较大的导数会累积。
    • 假设在一个多层神经网络中,某一层的激活函数输出使得下一层的输入刚好处于Sigmoid函数导数较大的区域(接近0.5),并且后续层的情况类似。那么在反向传播时,梯度就会因为这些较大导数的连乘而快速增大。
  5. 异常的数据分布或数据噪声

    • 如果训练数据中存在异常值或者噪声,并且这些异常值在计算损失函数和梯度时起到了主导作用,就可能导致梯度爆炸。
    • 例如,在回归问题中,如果数据集中有一个离群点,其目标值与其他数据点相差很大。在计算均方误差损失函数并反向传播时,这个离群点可能会导致梯度计算出现异常大的值。特别是当模型对这个离群点比较敏感时,会放大这种影响,使得梯度爆炸。





三、激活函数


  • 在神经网络的训练过程中,激活函数主要用于前向传播(Forward Propagation)阶段的神经元计算

  • 激活函数在隐藏层中的作用:

    • 控制神经元输出范围:例如,Sigmoid 函数的输出范围是(0,1),Tanh 函数的输出范围是(-1,1),在使用反向传播算法更新权重时,如果神经元的输出范围过大,可能会导致梯度消失或梯度爆炸问题。而通过合适的激活函数控制输出范围,可以在一定程度上缓解这些问题。

    • 引入非线性因素:如果没有激活函数,神经网络的每一层都只是对输入进行线性变换。而激活函数可以打破这种线性关系。例如,使用 ReLU 激活函数,多层神经网络通过激活函数的非线性作用,就可以逼近任何复杂的函数,从而能够更好地拟合数据中的复杂模式。


  • 激活函数在输出层中的作用:

    • 对于分类任务:多分类使用 Softmax 激活函数。Softmax 函数可以将神经元的输出转换为概率分布;对于二分类任务,Sigmoid 函数是常用的激活函数。

    • 对于回归任务:在回归任务中,输出层通常不使用激活函数,或者使用线性激活函数(即输出等于输入)。因为回归任务的目标是预测一个连续的值,不需要将输出转换为概率或限制在特定的范围内。





四、激活函数有哪些


  1. Sigmoid函数

    • 函数表达式及性质
    • 适用情况
      • 二分类问题的输出层:如在判断一封邮件是否为垃圾邮件。
      • 概率估计场景:如在医学诊断中,预测患者患有某种疾病的概率。
  2. Tanh函数(双曲正切函数)

    • 函数表达式及性质
    • 适用情况
      • 隐藏层:Tanh函数通常用于神经网络的隐藏层。与Sigmoid函数相比,它的输出范围更对称,中心在0点。这使得在反向传播过程中,梯度的更新更稳定。例如,在多层感知机(MLP)用于时间序列预测的隐藏层中,Tanh函数可以帮助模型更好地学习数据中的正负特征。
      • 需要输出中心为零的数据场景:当希望神经元的输出在正负区间都有分布,并且对数据的正负特征都比较敏感时,Tanh函数是比较合适的。比如在一些信号处理相关的神经网络应用中,Tanh函数可以更好地处理正负信号。
  3. ReLU函数(修正线性单元)

    • 函数表达式及性质
    • 适用情况
      • 隐藏层和输出层广泛应用:ReLU函数是目前深度学习中最常用的激活函数之一,广泛应用于神经网络的隐藏层和输出层。在图像识别、语音识别等众多领域的深度学习模型的隐藏层中,ReLU函数能够有效缓解梯度消失问题,加速模型的训练。例如,在卷积神经网络(CNN)用于图像分类任务时,如ResNet、VGG等模型的隐藏层大量使用ReLU函数。
      • 处理非负数据场景:如果数据本身具有非负的特性或者希望神经元输出非负的值,ReLU函数是一个自然的选择。例如,在处理图像像素值(通常是非负的)的神经网络中,ReLU函数可以很好地适应这种数据特性。
  4. Leaky ReLU函数

    • 函数表达式及性质
    • 适用情况
      • 缓解ReLU函数的“神经元死亡”问题:在一些情况下,ReLU函数可能会导致神经元“死亡”,即某些神经元在训练过程中永远不会被激活(输出始终为0)。Leaky ReLU函数通过为负数输入提供一个小的梯度,降低了这种风险。在一些对模型稳定性要求较高的应用中,如深度强化学习中的价值网络或者深度生成模型的某些部分,Leaky ReLU可以作为ReLU的替代选择。
  5. Softmax函数

    • 函数表达式及性质
    • 适用情况
      • 多分类问题的输出层:在神经网络用于多分类任务时,Softmax函数是输出层的常用激活函数。例如,在手写数字识别(MNIST数据集)任务中,输出层有(10)个神经元,经过Softmax函数后,这(10)个输出值分别表示数字(0 - 9)的概率,概率最高的类别即为预测的类别。Softmax 函数输出的所有概率之和是1






五、深度学习步骤详解


  • 迭代(Iteration):在训练模型时,一次迭代是指模型对一个批次(batch)的数据进行一次完整的前向传播和反向传播,并更新(在单批次训练情况下)或准备更新(在分布式训练情况下)参数的过程。在分布式训练中,一次迭代通常包含多个批次的数据。

  • Epoch:一个 Epoch 是指模型完整地遍历一次训练数据集。例如,如果训练数据集有 1000 个样本,批次大小(batch size)是 100,那么一个 Epoch 就包含 10 个批次,需要进行 10 次迭代来处理整个训练数据集。


  • EPOCHS:整个训练数据集被用于训练模型的次数,在每一个 EPOCH 中,整个训练过程会被重复执行

    • 随机初始化参数

    • 前向传播:模型对某一个batch的训练样本进行预测,计算输出(eg:训练集有1000条数据,每个batch中有100条数据,那么这一轮的EPOCH中会包含10个batch。该计算步骤会对batch里的每一条数据进行计算)

    • 损失计算:根据上一个步骤中的100个输出分别计算它们与真实值的损失,并使用某种损失函数。
      eg:

    • 反向传播:通过反向传播算法,模型调整其参数以减少损失。即计算损失相对于每个参数(即若干特征Wi和b)的梯度,然后更新参数

    • 迭代:对训练数据集中剩余的batch进行重复这上述几个步骤,直至完成一个 EPOCH


  • 为什么每次迭代学习会更改batch数据,而不是对某一个batch数据进行反复多次的迭代学习呢?

    • 提高泛化能力,避免过度拟合:如果模型只对一个特定的 batch 数据进行多次更新,它可能会在这个 batch 上表现得很好,但对其他数据的泛化能力可能会下降。通过在每个迭代中使用不同的 batch,模型能够接触到更多样化的数据,从而学习到更一般化的特征

    • 提高训练效率,快速收敛:通过多次使用不同的 batch,模型能够更快地接触到整个训练集,这能够加速收敛过程。尽早接触到各种样本可以让模型更快地调整其参数,以适应数据的整体分布

    • 减小计算负担:在大规模深度学习模型训练中,通常希望在合理的时间内完成训练,因此使用不同的 batch 来更新参数更为高效。


  • seed:随机种子,为了控制随机性。随机种子值相同时,每次运行代码,将获得相同的随机数序列,确保实验结果一致。

    • 可重复性:使用相同的Seed,可以复现他人的工作或自己之前的工作,使得模型训练和评估过程保持一致,使得结果能够被其他研究者验证和重现。

    • 调试:在调试模型时,使用相同的 seed 可以更容易分析和理解模型的行为,因为可以确定所有的随机因素都是相同的。

    • 比较实验:在进行不同模型或参数设置的比较时,使用相同的 seed 能保证所有实验在相同的数据划分和初始化条件下进行,有助于验证结果的有效性。


另外注意:分布式训练的参数更新制度和单批次训练的参数更新制度是不一样的

  • 单批次更新参数制度:每一个迭代只使用一个批次数据,一个epoch使用了所有批次数据。批次训练后调整模型参数是为了在处理下一个批次时,模型能够基于之前批次的训练结果进行更优化的预测。而整个 EPOCH 完成后,模型在整个训练数据集上得到了一次完整的训练和调整。

  • 分布式训练的参数更新制度:每一个迭代使用所有批次的数据(即所有训练数据),可以这么理解所有GPU的一次迭代就相当于一个epoch(但是也有可能 一次迭代使用了部分批次的数据,这个视具体情况而定)。处理每个批次数据时,没有立即更新模型参数,但在所有相关批次处理完后更新,具体看下面的例子:

    • 例如,有 100 个批次(batch_num 从 0 - 99),4 个 GPU(Rank0 - Rank3)参与训练。可能会将批次划分为每个 GPU 负责 25 个批次,在一轮训练中,Rank0 处理 batch_num 为 0 - 24 的批次,Rank1 处理 batch_num 为 25 - 49 的批次,Rank2 处理 batch_num 为 50 - 74 的批次,Rank3 处理 batch_num 为 75 - 99 的批次。(这是一次迭代训练完所有批次的数据的情况)

    • 在每一轮中,各个 GPU 并行处理分配给自己的批次,完成梯度计算后通过集合通信操作汇总梯度同步更新模型参数,然后进入下一轮训练。


  • 单批次和多分布训练实际中的差异

    • 数值精度差异:在实际操作中,由于计算机的数值精度限制,分布式训练和单批次训练可能会出现一些细微的差异。分布式训练涉及到多个计算节点之间的通信和梯度汇总,在这个过程中可能会引入一些数值计算上的误差。例如,在进行梯度的求和或平均操作时,由于浮点数的表示精度问题,可能会导致最终汇总的梯度与单批次训练中逐步计算得到的梯度存在一些小的偏差。

    • 收敛速度差异:分布式训练通常能够利用多个计算节点的并行计算能力,加速训练过程,更快地处理大量数据。相比之下,单批次训练每次只能处理一个批次的数据,在处理大规模数据时会花费更多的时间。而且,由于分布式训练可以在每一轮迭代中基于更多的数据样本(通过多个批次的并行处理)来更新模型参数,它可能会更快地收敛到一个较好的解。但是,如果分布式训练中的参数同步机制设置不当,例如通信开销过大或者梯度更新不同步,也可能会影响收敛速度和最终结果。

    • 过拟合与欠拟合差异:单批次训练由于每次只基于一个批次的数据更新参数,可能更容易受到个别批次数据特性的影响,导致模型在训练过程中出现过拟合或欠拟合的情况。例如,如果某一个批次的数据存在较大的噪声或者偏差,单批次训练可能会过度调整模型参数以适应这个有偏差的批次。而分布式训练由于综合了多个批次的数据信息来更新模型参数,相对来说更不容易受到个别批次数据特性的影响,能够更好地平衡模型的拟合程度。








posted @ 2024-11-14 19:44  卡卡发  阅读(40)  评论(0编辑  收藏  举报