zoukankan      html  css  js  c++  java
  • Batch normalization

    Batch normalization

    1. 为什么我们需要对特征做feature scaling?
      一句话解释就是为了让我们求解loss最低值的过程中更加的平稳和缓,容易收敛。
      具体解释可以看这里:
      特征工程中的「归一化」有什么作用? - 忆臻的回答 - 知乎
      https://www.zhihu.com/question/20455227/answer/197897298

    用我自己的话总结就是:损失函数对某个权重求梯度的时候,会用到这个权重之前的变量,如果这个白能量过大,会导致梯度过大,也就是这个权重在收敛的过程中每次变化量会很大,就不容易收敛。

    2.从上面这段话我们应用到深度学习中,如果在深度学习中,我们会对网络的输入做归一化,那么对于第一次层神经网络的输出也就是第二层神经网络的出入,我们当然也会想到进行归一化,
    这样我们才会在整个深度学习网络中确保了使神经网络的收敛变得更加的平缓容易。

    3.这就会出现一个问题就是我们对于整个神经网络的输入的数据也就是第一层的输入数据我们是可见的,也就是我们的原始数据,我们当然可以做到归一化或者说标准化。但是对于第二层第三层甚至以后几层,
    数据是流动在神经网络内部的,如果要计算它的标准差均值,我们要做的是把所有数据输入第一层之后,然后从第二层的数据中,统一计算均值和标准差,这个是很浪费时间的。
    而且我们的优化算法有些是有使用的输入一个batch的数据。而且最为关键的是由于第一层神经网络的权重是在不断变化的,导致每次第二层的输入数据分布都是有变化的,均值和标准差也都是有变化的。

    简单讲就是,我们需要的不仅仅是对第一层神经层的标准化,而是对神经网络中的每一层都进行标准化,这对神经网络的收敛很有帮助,解决了一个叫做internal Covariate shift的问题。
    经过神经网络

    4.进而我们引入batch normalization 。首先对于batch,我们知道在train的时候我们不是仅仅挑出一个数据来进行训练,而是挑出一个btach的数据,同时进行训练
    举个例子,我们如果batch为3,那么这三个数据是进行平行计算的。在GPU计算的过程中,我们可以这么理解,我们是把三个数据排在一起编程一个matrix,维度为[leng,batch_size],把
    这个matrix乘以权重matrix得到一个输出,现在就变成了一个matrix和matrix进行计算,这样肯定比权重matrix对三个数据进行单个运算更加的快捷。这就是GPU加速运算的原理。

    1. 我们可以把batch normalization放在激活函数的前面也可以放在激活函数的后面,但是我们一般是放在的激活函数的前面。这样的好处是我们可以确保我们激活函数的输入是放在了激活函数梯度比较大的部位

    2. 在对第一次数据的输出数据也就是第二层的输入数据进行normalization的时候,我们等待所有的数据训练完,然后对所有数据计算标准差和均值,这一点是不方便的。于是我们的事情就是,对batch内部的数据进行计算
      均值和标准差,这也就有一个要求就是我们在做batch normalization,我们使用batch内部的均值和方差和代表的了整个数据集的方差和数据,这就要求我们的batch不能小,要稍微的大一点

    3. 这里有一个问题,我们引入batch normalization的时候怎么进行反向传播。
      有个错误的想法是这样的:有的人认为我们在做标准化的时候,是减去了一个均值,除以了标准差。这个过程,我们涉及到的是都是常量,反向传播常量影响不大。

    权重是改变的,导致数据分布式改变的,也就是说均值和标准差也是改变的,不是一个常量

    1. 有这么一种情况,就是如果我们的激励函数并不是在均值为0标准差为1的条件下效果很好,而是在其他分布的条件下效果更好,这个时候我们要做的就是在标准化之后,我们在进行一个逼得操作,改为别的分布。这个时候我们就
      会增加两个新的参数,这两个参数是为了让我们的激励函数遇着更好的效果而添加进来的,我们把这个当成神经网络的参数,它可以在训练过程中被学习。

    9 在训练过程中,我们使用batch normalization进行训练更新参数,那么在测试过程中怎么办呢?在测试过程中,我们是存在一种情况就是我们输入的数据仅仅是一个数据,那么我们是没有办法在神经网络测试过程中,就算每一层
    输入的均值和标准差的。
    这个时候我们哟一个比较理想的方法就是在我们训练好神经网络之后,神经网络的参数已经不再发生变化,我们就可以把所有的训练数据统一导入到神经网络中,记录下每一层的均值和标准差,对测试的数据进行处理。
    但是这样做比较麻烦,我们在实际操作中是这样做的:在update过程中,我们把这个过程中所有均值和标准差都记录下来,然后我们的对这些均值和标准差进行一个权重加和作为我们在测试过程中均值和标准差。我们会在快收敛的时候
    的均值和标准差比较大的权重,update刚开始的权重小一些。

    10.第一个优点 如果我们没有normallization, 数据不容易收敛,那么我们就需要把learning rate设置的小一点,这样就比较麻烦。 有了这个之后,我们就可以设置的大一点,收敛的就快一点。
    还有一个优点,对解决梯度消失问题有帮助。如果我们使用了signmoid函数,数据有可能落在梯度很小的部分,有了标准化,数据落在了效果比较好梯度比较大的部分,这样梯度消失问题就不会很严重。
    第三个有点就是有了它可以让神经网络对于参数初始化的方法敏感度降低,也就是说参数初始化对于参数的影响也就没有那么大了。简单从数据上来讲,是如果参数很小,乘以K倍变得很大之后,对于第二层的输入不会有影响(26:37秒李宏毅)
    第四个有点就是可以缓解过拟合现象,相当于做了正则化。这一点很好解释,我们把每一层的输入都标准化,即使输入数据中部分噪声数据,但是关系不大,在一个batch中,我们会做标准化,把因为噪声差生的均值shiift和标准差shift在搞到正确的位置

    李宏毅batch-normalization

  • 相关阅读:
    7503E-M-irf2配置以及bfd配置
    nltk_29_pickle保存和导入分类器
    nltk_28Twitter情感分析模型
    美国在研新药_读取单个PDF
    Python:eval的妙用和滥用
    opencv_判断两张图片是否相同
    Make 命令教程
    pdf在线处理网站
    K-Means clusternig example with Python and Scikit-learn(推荐)
    自然语言27_Converting words to Features with NLTK
  • 原文地址:https://www.cnblogs.com/lzida9223/p/10972775.html
Copyright © 2011-2022 走看看