文章目录

  • 交叉熵目标函数更陡峭
  • Xavier initialization [1][4]
  • He initialization [2][3]
    • He init 考虑ReLU函数
    • He init 考虑Leaky ReLU函数
  • 结束语
  • 参考资料

交叉熵目标函数更陡峭

在论文[1]中给了一个图示,一定程度上说明了为什么Cross Entropy用的很多,效果很好。图中上面的曲面表示的是交叉熵代价函数,下面的曲面表示的是二次代价函数,W1和W2分别表示层与层之间的连接权值。

)

在1986年 Rumelhart 已经发现:logistic function 或者叫 conditional log-likelihood function: -log P(y|x) 的效果比 quadratic cost function(平方代价函数)的效果好很多的,原因在于 quadratic cost function(平方代价函数)在训练过程中会出现更多的 plateaus(平坦区域)。文章给出了一个两个参数下的图,图中采用的是具有单隐层的神经网络,激活函数使用的是 tanh 函数,对于输入信号进行随机初始化,可以看到二次代价函数具有更多的 plateaus (平坦区域)。

Xavier initialization [1][4]

早期的参数初始化方法普遍是将数据和参数初始化为标准高斯分布(均值0方差1),但随着神经网络深度的增加,这方法并不能解决梯度消失问题。


那么我们应该怎么通过初始化来缓解这个问题呢?
论文中首先给出了一个启发式的方法,想法是初始化值和神经元的输入个数有关:

We initialized the biases to be 0 and the weights Wij at each layer with the following commonly used heuristic, where U[−a, a] is the uniform distribution in the interval (−a, a) and n is the size of the previous layer (the number of columns of W)

W∼U[−1n,1n]Var(W)=13nW \sim U[-\frac{1}{\sqrt n},\frac{1}{\sqrt n}]\\ Var(W) = \frac{1}{3n}W∼U[−n​1​,n​1​]Var(W)=3n1​

上面式子中,W∼W \simW∼表示其中的每一个元素WijW_{ij}Wij​都是符合一个均匀分布的。其中n表示本层的输入size,也就是上一层的输出size。我们知道随机变量在[a,b] 间的均匀分布的方差为
Var=(b−a)212Var= \frac{(b-a)^2}{12}Var=12(b−a)2​
所以得到权重参数的方差是1/3n。先记一下,后面分析会讲到。

为了便于研究,作者假设使用线性激活函数f(x)f(x)f(x),且在零点导数f′(0)=1f'(0)=1f′(0)=1。实际上,作者研究的是参数的线性区域,可以认为是对任务的一个简化。

对于一层网络:
f(x)=∑inwixi+bf(\textbf x) = \sum_i^n w_ix_i + bf(x)=i∑n​wi​xi​+b
输出的方差:
Var(f(x))=∑inVar(wixi)Var(f(\textbf x)) = \sum_i^n Var(w_i x_i)Var(f(x))=i∑n​Var(wi​xi​)
其中每一项:
Var(wixi)=E[wi]2Var(xi)+E[xi]2Var(wi)+Var(wi)Var(xi)Var(w_i x_i) = E[w_i]^2Var(x_i) + E[x_i]^2Var(w_i)+Var(w_i)Var(x_i)Var(wi​xi​)=E[wi​]2Var(xi​)+E[xi​]2Var(wi​)+Var(wi​)Var(xi​)

当我们假设输入和权重都是0均值时(目前有了BN之后,每一层的输入也较容易满足),即E[xi]=E[wi]=0E[x_i] = E[w_i] = 0E[xi​]=E[wi​]=0,上式可以简化为:

Var(wixi)=Var(wi)Var(xi)Var(w_i x_i) =Var(w_i)Var(x_i)Var(wi​xi​)=Var(wi​)Var(xi​)

由于w和x独立同分布,那么输出的方差就是

Var(f(x))=nVar(wi)Var(xi)Var(f(\textbf x)) = n Var(w_i) Var(x_i)Var(f(x))=nVar(wi​)Var(xi​)

我们发现,输出的方差是和输入的方差是一个线性倍数关系。假设ziz^izi是第iii层的输入向量,sis^isi是第iii层激活函数的输入,fff表示激活函数

si=ziWi+bizi+1=f(si)si+1=zi+1Wi+1+bi+1\textbf s^i = \textbf z^i W^i + \textbf b^i \\ \textbf z^{i+1} = f(\textbf s^i)\\ \textbf s^{i+1} = \textbf z^{i+1} W^{i+1} + \textbf b^{i+1} si=ziWi+bizi+1=f(si)si+1=zi+1Wi+1+bi+1

可以得到:
对于一个多层的网络,某一层的方差可以用累积的形式表达:
Var[zi]=Var[x]∏i′=0i−1ni′Var[Wi′]Var[z^i] = Var[x] \prod_{i'=0}^{i-1}n_{i'} Var[W^{i'}] Var[zi]=Var[x]i′=0∏i−1​ni′​Var[Wi′]

求反向我们可以得到(假设f′(ski)≈1f'(s_k^i) \approx 1f′(ski​)≈1,其中Cost表示Loss):
∂Cost∂ski=f′(ski)Wk,⋅i+1∂Cost∂si+1∂Cost∂wl,ki=zli∂Cost∂ski\frac{\partial Cost}{\partial s_k^i} = f'(s_k^i) W_{k,\cdot}^{i+1} \frac{\partial Cost}{\partial s^{i+1}} \\ \frac{\partial Cost}{\partial w_{l,k}^i} = z_l^i \frac{\partial Cost}{\partial s_k^i}∂ski​∂Cost​=f′(ski​)Wk,⋅i+1​∂si+1∂Cost​∂wl,ki​∂Cost​=zli​∂ski​∂Cost​

其中Var[Wi′]Var[W^{i'}]Var[Wi′]表示第i′i'i′层的共享权重的方差,对于ddd层的网络(大饼博士注:下面第一个式子的变量的layer号,符号上和上面求∂Cost∂ski\frac{\partial Cost}{\partial s_k^i}∂ski​∂Cost​的式子,有一点歧义难看懂。主要上面是正向去写,在同一个层里面SiS^iSi和Wi+1W^{i+1}Wi+1是一对。而下面第一个式子,理解成同一个层里面输入以及参数都是对应的i′i'i′,通过堆叠ddd层,得到最初的输入sis^isi的梯度的方差)
Var[∂Cost∂si]=Var[∂Cost∂sd]∏i′=idni′+1Var[Wi′]Var[∂Cost∂wi]=∏i′=0i−1ni′Var[Wi′]∏i′=id−1ni′+1Var[Wi′]×Var[x]Var[∂Cost∂sd]Var[\frac{\partial Cost}{\partial s^i}]=Var[\frac{\partial Cost}{\partial s^d}] \prod_{i'=i}^{d}n_{i'+1} Var[W^{i'}] \\ Var[\frac{\partial Cost}{\partial w^i}]= \prod_{i'=0}^{i-1}n_{i'} Var[W^{i'}] \prod_{i'=i}^{d-1}n_{i'+1} Var[W^{i'}] \times Var[x] Var[\frac{\partial Cost}{\partial s^d}]Var[∂si∂Cost​]=Var[∂sd∂Cost​]i′=i∏d​ni′+1​Var[Wi′]Var[∂wi∂Cost​]=i′=0∏i−1​ni′​Var[Wi′]i′=i∏d−1​ni′+1​Var[Wi′]×Var[x]Var[∂sd∂Cost​]

如果我们希望,神经网络在前向计算的时候,输入输出的方差都是一致的,即∀(i,i′),Var[zi]=Var[zi′]\forall (i,i'), Var[z^i] = Var[z^{i'}]∀(i,i′),Var[zi]=Var[zi′],我们需要满足:

∀i,niVar[Wi]=1\forall i, \quad n_i Var[W^i] = 1∀i,ni​Var[Wi]=1

类似的,如果我们希望反向计算的输入输出方差也是一致的,∀(i,i′),Var[∂Cost∂si]=Var[∂Cost∂si′]\forall (i,i'), Var[\frac{\partial Cost}{\partial s^i}] = Var[\frac{\partial Cost}{\partial s^{i'}}]∀(i,i′),Var[∂si∂Cost​]=Var[∂si′∂Cost​],需要满足:

∀i,ni+1Var[Wi]=1\forall i, \quad n_{i+1} Var[W^i] = 1∀i,ni+1​Var[Wi]=1

一个层的输入输出一般不相同,作为折中

∀i,Var[Wi]=2ni+ni+1\forall i, \quad Var[W^i] = \frac{2}{n_i + n_{i+1}}∀i,Var[Wi]=ni​+ni+1​2​

这个就是Xavier初始化算法,认为神经网络每一层的参数的方差需要满足的方差(均值=0)。(注:这里并没有假设是符合什么分布的,只是要求方差是这样,所以理论上我们可以采用任意分布,只要方差等于上面的公式即可)。

常见的,我们可以用高斯分布,或者均匀分布来生成随机参数(对于Xavier初始化方式,例如pytorch提供了uniform和normal两种:)。

  • 如果是采用均匀分布,根据前面讲过的,随机变量在[a,b] 间的均匀分布的方差为Var=(b−a)2/12Var= {(b-a)^2}/{12}Var=(b−a)2/12,那么我们只要用下面分布来采样,就可以得到上面的方差。这个公式也是Xavier论文[1]中给出的建议。

W∼U[−6nj+nj+1,6nj+nj+1]W \sim U[-\frac{\sqrt 6}{\sqrt {n_j + n_{j+1}}},\frac{\sqrt 6}{\sqrt {n_j + n_{j+1}}}]W∼U[−nj​+nj+1​​6​​,nj​+nj+1​​6​​]

  • 如果是采用高斯分布,那么直接就:[6]

W∼N(0,2ni+ni+1)W \sim N(0, { \frac{2}{n_i + n_{i+1}}})W∼N(0,ni​+ni+1​2​)

补充一句,caffe的Xavier实现有三种选择[7]:

He initialization [2][3]

前面Xavier方法只考虑了线性激活函数,而现在的神经网络(特别是CNN网络)采用的主要是ReLU和Leaky ReLU函数,He初始化方法就是来分析采用ReLU和Leaky ReLU激活函数下,如果我们希望每一层的输入输出方差不变,我们应该如何初始化权重参数,方法上和前一节基本一致。

对于一个卷积层或者全连接层,其表达式为

yl=Wlxl+bl.y_l = W_l x_l + b_l.yl​=Wl​xl​+bl​.

若WlW_lWl​、blb_lbl​采样自0均值高斯分布,用nln_lnl​表示第lll层xlx_lxl​的维数,在卷积层,有nl=k2cn_l=k^2cnl​=k2c,kkk为卷积核的边长,ccc为channel数,注意到yly_lyl​是WlW_lWl​中元素与xlx_lxl​中对应元素的乘积的和,则上式各变量的方差关系可以表示为:

Var[yl]=nlVar[Wlxl]=nlVar[Wl]E[xl2].Var[y_l] = n_l Var[W_l x_l]=n_l Var[W_l]E[x_l^2].Var[yl​]=nl​Var[Wl​xl​]=nl​Var[Wl​]E[xl2​].

这里的xlx_lxl​项前并不是其方差,而是E[xl2]E[x^2_l]E[xl2​],因为xlx_lxl​通常并不具备0均值,例如ReLU激活函数得到的结果,xlx_lxl​均为正值。注意到由于WlW_lWl​是0均值的,所以无论xlx_lxl​均值为多少,均有

E[yl]=E[Wlxl]=0.E[y_l]=E[W_l x_l]=0.E[yl​]=E[Wl​xl​]=0.

He init 考虑ReLU函数

通过ReLU激活函数:xl=max(0,yl−1)x_l=max(0,y_{l−1})xl​=max(0,yl−1​),仅正半轴有值,我们假设激活之前的值正负各一半,总体是对称的,可以得到:
E[xl2]=12Var[yl−1].E[x_l^2] = \frac{1}{2} Var[y_{l-1}].E[xl2​]=21​Var[yl−1​].

因此(如果本文从上面看下来的话,看到这个公式就很熟悉了):
Var[yl]=12nlVar[Wl]Var[yl−1].Var[y_l] = \frac{1}{2} n_l Var[W_l]Var[y_{l-1}].Var[yl​]=21​nl​Var[Wl​]Var[yl−1​].

我们希望每一层的激活前值(卷积的结果,没有过激活函数)的方差一致,Var[yl]=Var[yl−1]Var[y_l]=Var[y_{l-1}]Var[yl​]=Var[yl−1​],这个是和Xavier不一样的地方,这样就可以不考虑激活函数了。那么:

12nlVar[Wl]=1.\frac{1}{2} n_lVar[W_l] =1.21​nl​Var[Wl​]=1.

  • 如果是用高斯分布采样,W∼N(0,2nl)W \sim N(0,\frac{2}{n_l})W∼N(0,nl​2​)

  • 如果是用均匀分布,那么:W∼U[−6/nl,6/nl]W \sim U[-\sqrt{6/n_l},\sqrt{6/n_l}]W∼U[−6/nl​​,6/nl​​]

He init 考虑Leaky ReLU函数

Leaky ReLU激活函数和导函数分别为

所以:
E[xl2]=12(1+α2)Var[yl].E[x_l^2] = \frac{1}{2}(1+\alpha^2) Var[y_l].E[xl2​]=21​(1+α2)Var[yl​].

类似上面的推导,可以得到,

12(1+α2)nlVar[Wl]=1.\frac{1}{2}(1+\alpha^2) n_lVar[W_l] =1.21​(1+α2)nl​Var[Wl​]=1.

  • 如果是用高斯分布采样,W∼N(0,2(1+α2)nl)W \sim N(0,\frac{2}{(1+\alpha^2) n_l})W∼N(0,(1+α2)nl​2​)

  • 如果是用均匀分布,那么:W∼U[−6/(1+α2)nl,6/(1+α2)nl]W \sim U[-\sqrt{6/(1+\alpha^2) n_l},\sqrt{6/(1+\alpha^2) n_l}]W∼U[−6/(1+α2)nl​​,6/(1+α2)nl​​]

结束语

好了,到这里本篇就讲完了,介绍了Xavier与He intit的初始化方法,是非常常见的方法。后来还有很多工作来优化初始化,比如进一步考虑resnet网络结构时,有文章引入了Mean field,还有fixup initialization等方法。这些以后有机会再写了。最后说一句BN,因为可以强制要求每一层的数据符合0均值1方差,所以效果上和本文讨论的方法效果很类似。使得前向的数据会相对稳定。但是BN似乎并没有考虑反向梯度的稳定性,这一点目前更多是让resnet中的identity跳边来完成的,有这个identity跳边情况下,梯度至少在在跳边这一路上,可以identity透传,梯度就不容易消失。但是似乎梯度爆炸没有避免,什么情况下会爆炸呢?回看我们前面的分析,比如Xavier中,我们要求ni+1Var[Wi]=1\quad n_{i+1} Var[W^i] = 1ni+1​Var[Wi]=1,反向就会稳定,如果>1,那么很显然,只要层数深,梯度就指数爆炸了,这样训练也会很难训。因此训练过程中的数据和梯度的稳定性是很重要的。

参考资料

[1] Understanding the difficulty of training deep feedforward neural networks
[2] Delving Deep into Rectifiers: Surpassing Human-Level Performance on ImageNet Classification
[3] https://blog.csdn.net/happynear/article/details/45440811
[4] https://blog.csdn.net/kangroger/article/details/61414426
[5] https://blog.csdn.net/qq_34784753/article/details/78668884
[6] https://blog.csdn.net/dss_dssssd/article/details/83959474
[7] https://blog.csdn.net/weixin_34221773/article/details/86085462
[8] https://www.cnblogs.com/itmorn/p/11132494.html#ct5

深度学习方法(二十一):常用权重初始化方法Xavier,He initialization的推导相关推荐

  1. 权重初始化方法及适用情况

    1. Gaussian 从具有固定均值(例如0)和固定2的标准差(例如0.01)的搞死分布中随机抽取权重,这是最常用的. 一般使用截断高斯. 2. Xavier 这种方法是但的缩放均值或者搞死分布进行 ...

  2. 几种常用的权重初始化方法

    来源:投稿 作者:175 编辑:学姐 在深度学习中,权重的初始值非常重要,权重初始化方法甚至关系到模型能否收敛.本文主要介绍两种权重初始化方法. 为什么需要随机初始值 我们知道,神经网络一般在初始化权 ...

  3. C语言二维数组的初始化方法

    C语言二维数组的初始化方法 01 完全赋值式一 int x[3][4]={{1,2,3,4}{5,6,7,8},{9,10,11,12}}; 02 完全赋值式二 int x[3][4]={1,2,3, ...

  4. PyTorch学习笔记:针对一个网络的权重初始化方法

    # 针对一个网络的权重初始化方法 import torch import torch.nn as nn## 建立一个测试网络 class TestNet(nn.Module):def __init__ ...

  5. 吴恩达深度学习L2W1——神经网络权重初始化方法、正则化

    文章目录 神经网络的初始化 初始化数据 模型搭建 简单函数 零初始化--initialize_parameters_zeros 随机初始化--initialize_parameters_random ...

  6. 基于Detectron2模型和深度学习方法的改进森林火灾检测方法

     1.文章信息 本次介绍的文章是来自韩国科研团队的一篇2023年火灾检测文章,文章立足于森林火灾检测,题目为<An Improved Forest Fire Detection Method B ...

  7. 深度学习之四:常用模型和方法

     九.Deep Learning的常用模型或者方法 9.1.AutoEncoder自动编码器 Deep Learning最简单的一种方法是利用人工神经网络的特点,人工神经网络(ANN)本身就是具有 ...

  8. 二维vector数组初始化方法

    在用devcpp编译程序时发现,二维vector数组如果只定义的话,不指定元素个数也不进行初始化的时候会导致编译出错. 通常情况下,可以只提供vector对象容纳的元素数量而略去初始值.此时库会创建一 ...

  9. 大众汽车用html写出来代码,大众车系常用系统初始化方法及匹配编码

    一.新迈腾B7天窗初始化方法 天窗开到上翘位置后无法关闭,开关不论旋到什么位置玻璃只是下来再翘上去. 故障诊断过程: 1.连接VAS 5052A查询各系统有无故障记忆包括舒适系统无任何故障记录. 2. ...

最新文章

  1. DOM操作之属性和样式操作
  2. 使用Hash碰撞进行DoS攻击
  3. linux中特殊字符反引号,linux中的特殊符号$ ‘’ 反引号 反斜杠
  4. 目标检测——夏侯南溪模型搭建篇(legacy)
  5. spring boot开发环境搭建
  6. (day 40 - 双指针+库函数) 剑指 Offer 58 - I. 翻转单词顺序
  7. NOIP2013 复盘
  8. MacOS Big Sur 11.2.3 (20D91) with Clover 5131 and OC 0.6.7 and PE 三EFI分区原版DMG黑苹果镜像
  9. luogu p1330封锁阳光大学
  10. 深入浅出CNN-经典总结(2019中秋)
  11. 统信uos设置静态IP
  12. C. Multiples of Length 思维构造
  13. 【服务器】本地运行成功,但服务器上运行却显示错误500
  14. 大数据分析6个核心技术
  15. RFID手持机助力仓储物流信息化管理
  16. unity 模拟弹簧
  17. 华清远见嵌入式开发学习的6大阶段
  18. 无人驾驶汽车的工作原理
  19. ListView多选操作模式详解
  20. DL基本知识(五)神经网络经典模型

热门文章

  1. python定义变量类型为数字_python 学习(四)- 变量类型
  2. vue中js转换火星坐标以及真实坐标
  3. selenium工作原理详解
  4. 以太坊(Ethereum) - 让浏览器支持区块链(MetaMask)
  5. 微信小程序布局快速入门
  6. 【webpack】输入npm run dev报错: This is probably not a problem with npm. There is likely additional loggin
  7. Python基础(十二)——循环语句
  8. 技术管理者的困惑——技术与管理应该如何平衡?
  9. 股票自选股基本函数大全-3
  10. 字节跳动数据中台的 Data Catalog 系统搜索实践