全连接神经网络
- 1.全连接神经网络基本概念
-
- 1.1基本表达式
- [1.2 全连接神经网络的权值](#1.2 全连接神经网络的权值)
- [1.3 全连接神经网络与线性不可分](#1.3 全连接神经网络与线性不可分)
- [1.4 全连接神经网络绘制与命名](#1.4 全连接神经网络绘制与命名)
- 2.激活函数
-
- [2.1 为什么需要非线性操作](#2.1 为什么需要非线性操作)
- [2.2 常用的激活函数](#2.2 常用的激活函数)
- 2.3.网络结构设计
- 2.4.全连接神经网络小结
- 3.SOFTMAX与交叉熵
-
- [3.1 SOFTMAX](#3.1 SOFTMAX)
- [3.2 交叉熵损失](#3.2 交叉熵损失)
- [3.3 交叉熵损失VS多类支撑向量机损失](#3.3 交叉熵损失VS多类支撑向量机损失)
- 4.计算图
-
- [4.1 什么是计算图](#4.1 什么是计算图)
- [4.2 计算图与反向传播算法](#4.2 计算图与反向传播算法)
- [4.3 计算图总结](#4.3 计算图总结)
- [4.4 反向传播示例](#4.4 反向传播示例)
- 4.5、反向传播(从右到左,求每个节点的梯度)
- [4.5 计算图的颗粒度](#4.5 计算图的颗粒度)
- [4.6 计算图中常见的们单元](#4.6 计算图中常见的们单元)
- 5.再看激活函数
-
- [5.1 各种激活函数](#5.1 各种激活函数)
- [5.2 梯度爆炸](#5.2 梯度爆炸)
- [5.3 激活函数选择总结](#5.3 激活函数选择总结)
- 6.梯度算法改进
-
- [6.1 梯度下降算法存在的问题](#6.1 梯度下降算法存在的问题)
- [6.2 动量法](#6.2 动量法)
- [6.2 动量法](#6.2 动量法)
- [6.3 自适应梯度与RMSProp(靠不同方向取不同的步长来实现)](#6.3 自适应梯度与RMSProp(靠不同方向取不同的步长来实现))
- [6.4 ADAM(前两种方法的结合)](#6.4 ADAM(前两种方法的结合))
- [7 .权值初始化](#7 .权值初始化)
- Xavier初始化
- 权值初始化小结
- 8.批归一化
- 批归一化

1.全连接神经网络基本概念
1.1基本表达式
全连接神经网络级联多个变换来实现输入到输出的映射
两层全连接网络: f = W 2 max ( 0 , W 1 x + b 1 ) + b 2 f = W_2 \max(0, W_1 x + b_1) + b_2 f=W2max(0,W1x+b1)+b2
其中W1X+b1是一次线性变化,加上外层以后就是第二次线性变换了
三层全连接网络
f = W 3 max ( 0 , W 2 max ( 0 , W 1 x + b 1 ) + b 2 ) f = W_3 \max\left(0, W_2 \max\left(0, W_1 x + b_1\right) + b_2\right) f=W3max(0,W2max(0,W1x+b1)+b2)
注意:max是不可以去掉的,否则就变为了线性的了.max代表每个元素都和0比较一下,比0小的都变为0.
W2的行数是固定的与类别数相同,而W1的行数可以人为指定
1.2 全连接神经网络的权值
线性分类器 : f ( x , W ) = W x + b f(x, W) = Wx + b f(x,W)=Wx+b
线性分类器里面的W可以看做模版,模版个数由类别个数决定
两层全连接神经网络: 全连接神经网络里面W1可以看做模版,模版个数人为指定.
W2融合着多个模版匹配结果来实现最终类别打分.
问题: 那认为指定的W1额行数有什么作用呢?
答:比如下面的第8个模版是马的模版,模版里面有两个头,这是由马的信息平均而来的,而真实的马是没有这样的.所以这个模版的记录是不准确的.但是如果我们的模版数量够多,各种马的模版都有,就有机会学到真正的马是长的什么样.这就是W1的作作用.
例如原来只有10个类,但是我可以把W1指定为100,就有100个模版,而这100个模版里面就可以有几个去存储马得到模版了.
W1的行数由自己设置,列数有X1的维度决定
下面是权值模版

f = W 2 max ( 0 , W 1 x + b 1 ) + b 2 f = W_2 \max(0, W_1 x + b_1) + b_2 f=W2max(0,W1x+b1)+b2
全连接神经网络的描述能力更强.因为调整W1行数等于增加模版个数,分类器有机会学到两个不同方向马的模版.
1.3 全连接神经网络与线性不可分
两层全连接网络:
f = W 2 max ( 0 , W 1 x + b 1 ) + b 2 f = W_2 \max(0, W_1 x + b_1) + b_2 f=W2max(0,W1x+b1)+b2
线性分类器:
f ( x , W ) = W x + b f(x, W) = Wx + b f(x,W)=Wx+b
线性可分就是至少存在一个线性分界面能把两类样本没有错误的分开

而对于线性不可分的情况就是下面的图

对于这种线性不可分就要去使用两层全连接网络了
1.4 全连接神经网络绘制与命名

输入层维度:3072维
隐层的维度:100维,也就是模版的个数
输出层:维度是固定的,由类别数来决定
由于前层的神经元要与所有的神经元相连接,所以为全连接网络
N层全连接神经网络----除了输入层以外其它层数的数量为N的网络
全连接神经网络也叫多层感知器
2.激活函数
2.1 为什么需要非线性操作
f = W 3 max ( 0 , W 2 max ( 0 , W 1 x + b 1 ) + b 2 ) f = W_3 \max\left(0, W_2 \max\left(0, W_1 x + b_1\right) + b_2\right) f=W3max(0,W2max(0,W1x+b1)+b2)
max就是激活函数
如果网络中缺少了激活函数,那么全连接神经网络将变成一个线性分类器
去掉激活函数:
f = W 3 ( W 2 ( W 1 x + b 1 ) + b 2 ) + b 3 = W 3 W 2 W 1 x + ( W 3 W 2 b 1 + W 3 b 2 + b 3 ) = W ′ x + b ′ \begin{aligned} f &= W_3(W_2(W_1 x + b_1) + b_2) + b_3 \\ &= W_3 W_2 W_1 x + (W_3 W_2 b_1 + W_3 b_2 + b_3) \\ &= W' x + b' \end{aligned} f=W3(W2(W1x+b1)+b2)+b3=W3W2W1x+(W3W2b1+W3b2+b3)=W′x+b′
2.2 常用的激活函数

从图可以看出这个函数将太大的值变为1,太小的值变为0,将整个向量限制在(0,1)里面

大于0就是a,小于0就是0.

将向量数据压缩在[-1,1]之间.

2.3.网络结构设计
1.用不用隐层,用一个还是多个?(深度设计)
2.每个隐层设置多少个神经元比较合适?(宽度设计)
3.激活函数的设计

结论:神经元个数越多,分界面就越复杂,在这个集合上的分类能力就越强
依据分类任务的难易程度来调整神经网络模型的复杂程度.分类任务越难,我们设计的神经网络就应该给越深,越宽.但是,需要注意的是对训练集分类精度最高的全连接神经网络模型,在真实场景下识别性能未必最好(过拟合).
2.4.全连接神经网络小结
1.激活函数是作用在神经元上的,作用在线性变化后的结果上,输入层一般用预处理来实现
2.全连接神经网络组成:一个输入层一个输出层以及多个隐层
2.输入层与输出层的神经元个数由任务决定而隐层数量以及每个隐层的神经元个数由人为指定
3.激活函数是全连接神经网络中的一个重要部分,缺少了激活函数,全连接神经网络将退化为线性分类器
3.SOFTMAX与交叉熵
3.1 SOFTMAX
两层全连接网络: f = W 2 max ( 0 , W 1 x + b 1 ) + b 2 f = W_2 \max(0, W_1 x + b_1) + b_2 f=W2max(0,W1x+b1)+b2

假如这里要把X1判断为是什么类,也就是看f1到fc的哪个输出值是最大,比如f2的输出值最大那么x1就是就是第二类,这里f1到fc是一个分数在,f的取值范围是R,但是做出这个决策正确的概率有多少呢?
答:经过SOFTMAX操作后的输出层就是一个概率分布

假如P2为0.8就代表这个样本为第二类的概率为0.8
简单来说SOFTMAX就是将原来的分数f取 e f c e^{f_c} efc 得到一个新的分数t再将新分数进行归一化 t c ∑ j t j \frac{t_c}{\sum_{j} t_j} ∑jtjtc得到P,而P1+P2+...+Pc=1
下面举一个例子:

3.2 交叉熵损失


右边这个真实分布中只有一个概率为1,其余都为0的分布叫做one-hot
将预测值与真实值进行比较来度量当前分类器的性能
现在的问题是,如何度量现在的分类器输出与预测值之间的距离

要确定某个样本是哪一类更加可信,也就是要让这两个分布越接近越好.像这里就是说预测值里面的bird的越接近1越好,cat,car越接近0越好.
而要比较两个分布之间的距离就要使用到交叉熵损失,当两个分分布值越接近交叉熵越小
-
熵:
H ( p ) = − ∑ x p ( x ) log p ( x ) H(p) = -\sum_{x} p(x) \log p(x) H(p)=−x∑p(x)logp(x) -
交叉熵:
H ( p , q ) = − ∑ x p ( x ) log q ( x ) H(p, q) = -\sum_{x} p(x) \log q(x) H(p,q)=−x∑p(x)logq(x) -
相对熵:
K L ( p ∥ q ) = − ∑ x p ( x ) log q ( x ) p ( x ) KL(p \parallel q) = -\sum_{x} p(x) \log \frac{q(x)}{p(x)} KL(p∥q)=−x∑p(x)logp(x)q(x)
相对熵(relative entropy)也叫KL散度(KL divergence);用来度量两个分布之间的不相似性(dissimilarity)。也就是判断p与q多么的不相似
三者之间关系:
H ( p , q ) = − ∑ x p ( x ) log q ( x ) = − ∑ x p ( x ) log p ( x ) − ∑ x p ( x ) log q ( x ) p ( x ) = H ( p ) + K L ( p ∥ q ) \begin{aligned} H(p, q) &= -\sum_{x} p(x) \log q(x) \\ &= -\sum_{x} p(x) \log p(x) - \sum_{x} p(x) \log \frac{q(x)}{p(x)} \\ &= H(p) + KL(p \parallel q) \end{aligned} H(p,q)=−x∑p(x)logq(x)=−x∑p(x)logp(x)−x∑p(x)logp(x)q(x)=H(p)+KL(p∥q)

在这种情况下三个H§均为0,那什么时候H§最大呢?
答:当三种可能一样大的时候[1/3,1/3,1/3]
真实分布[1,0,0]的H( p)=0,此时H (p,q)=KL(p//q),即kl散度就等于交叉熵,所以可以用交叉熵来度量两个分布之间的距离.
如何衡量两个随机分布的差异
交叉熵:
H ( p , q ) = − ∑ i = 1 c p ( x i ) log ( q ( x i ) ) H(p, q) = -\sum_{i=1}^{c} p(x_i) \log(q(x_i)) H(p,q)=−i=1∑cp(xi)log(q(xi))
注意:
真实分布为one-hot形式时交叉熵损失简化为
如果出现[0.95,0.3,0.2]这种情况,就不可以使用交叉熵这个概念了,这是就只能去使用KL散度计算两个分布之间的距离了. L i = − log ( q j ) L_i = -\log(q_j) Li=−log(qj),其中 j j j 为真实类别
交叉熵损失:
L i = − ∑ i = 1 c p ( x i ) log ( q ( x i ) ) L_i = -\sum_{i=1}^{c} p(x_i)\log(q(x_i)) Li=−i=1∑cp(xi)log(q(xi))
其中, p ( x i ) p(x_i) p(xi) 为标签的真实分布, q ( x i ) q(x_i) q(xi) 为模型预测的分布。
3.3 交叉熵损失VS多类支撑向量机损失

注:上面分数的0.6代表正确类别的分数


上面这个表就可以反映交叉熵损失与多类支撑向量机损失的区别.(绿色的分数是正确类别的分数)
对于多类支撑向量机损失每个分数里的正确类别的分数都大于等于其他类别分数1以上,所以都是0
而在交叉熵损失里[10,-2,3]和[10,-100,-100]都接近于0,但是[10,9,9]为0.24,比较大,这是因为真实类别并不比非真实类比的可能性多少.
通俗一点说,多类支撑向量机损失就是只要真是类别比其他的类别的分数大于1那么损失就是0,至于大多少是没有体现的.而交叉熵损失则是真实类别的分数比其他的类别的分数大的越多损失就越小.
那么使用交叉熵损失有些什么坏处呢?
像下面这种情况:分数为->[0.35,0.32,0.33],[0.333,0.333,0.334]其中第一个分数为正确类别的分数,这两个分类器的交叉熵损失差不多,但是第一个是预测正确的,但是第二个是预测失败的.所以当进行训练的时候,大量出现[0.35,0.32,0.33的时候会发现总损失一直没有变化但是精度不断提高。
4.计算图
4.1 什么是计算图
计算图是一种有向图,它用来表达输入,输出以及中间变量之间的计算关系,图中每个节点对应着一种数学运算.
4.2 计算图与反向传播算法


4.3 计算图总结
任意复杂的函数都可以用计算图形式表示
在整个计算图中,每个单元都会得到一些输入,然后进行下面两个计算,
1.这个门的输出值
2.其输出值关于输入值的局部梯度
利用链式法则,门单元应该将回传的梯度乘以它对其输入的局部梯度,从而得到整个网络的输出对该门单元的每个输入值的梯度
4.4 反向传播示例

f ( w , x ) = 1 1 + e − ( w 0 x 0 + w 1 x 1 + w 2 ) f(w, x) = \frac{1}{1 + e^{-(w_0x_0 + w_1x_1 + w_2)}} f(w,x)=1+e−(w0x0+w1x1+w2)1
注意:要进行反向计算先要把前向计算算完
4.5、反向传播(从右到左,求每个节点的梯度)
反向传播的核心是链式法则:
∂ f ∂ x = ∂ f ∂ y ⏟ 上游梯度 × ∂ y ∂ x ⏟ 局部梯度 \frac{\partial f}{\partial x} = \underbrace{\frac{\partial f}{\partial y}}{\text{上游梯度}} \times \underbrace{\frac{\partial y}{\partial x}}{\text{局部梯度}} ∂x∂f=上游梯度 ∂y∂f×局部梯度 ∂x∂y
我们从最右边的输出开始,一步步往回走:
第1步:最右侧的 1 / x 1/x 1/x 节点
- 输入值: x = 1.14 x = 1.14 x=1.14
- 输出值: f = 1 / 1.14 ≈ 0.88 f = 1/1.14 \approx 0.88 f=1/1.14≈0.88
- 函数: f ( x ) = 1 / x f(x) = 1/x f(x)=1/x,导数为 f ′ ( x ) = − 1 / x 2 f'(x) = -1/x^2 f′(x)=−1/x2
- 局部梯度: f ′ ( 1.14 ) = − 1 / ( 1.14 ) 2 ≈ − 0.77 f'(1.14) = -1/(1.14)^2 \approx -0.77 f′(1.14)=−1/(1.14)2≈−0.77
- 上游梯度:我们对输出求导,所以初始的上游梯度是 1(即 ∂ f ∂ f = 1 \frac{\partial f}{\partial f} = 1 ∂f∂f=1)
- 传给左边节点的梯度: 1 × ( − 0.77 ) = − 0.77 1 \times (-0.77) = -0.77 1×(−0.77)=−0.77
这就是图里红框标出来的计算:
1.00 × − 1 1.14 2 = − 0.77 1.00 \times \frac{-1}{1.14^2} = -0.77 1.00×1.142−1=−0.77
上面这一步就是反向计算的第一步,其他的就不多说了,最终结果如下图

注意:链式法则从右向左一直在相乘,所以链式法则一直在做乘法,在这个过程中如果梯度都比较小,那每乘以次局部梯度,数值就下降一次,可能最后局部梯度就没有了.这叫做梯度消失.
梯度消失是神经网络训练中非常致命的一个问题,其本质是由于链式法则的乘法特性导致的。
4.5 计算图的颗粒度
如果将上面那个例子的多个步骤看做一个整体,作为一次计算,就像下面这几部合成一步

将这几个步骤合成一步以后就是下面的公式

这样将几步操作合成一个步骤后颗粒度就变大了,像之前一步一步计算就是低颗粒度
4.6 计算图中常见的们单元


5.再看激活函数
5.1 各种激活函数

梯度特性不好,所以Sigmoid函数一般不用了



5.2 梯度爆炸
梯度爆炸也是由链式法则的特性导致的

梯度爆炸:断崖处梯度乘以学习率以后会是一个非常大的值,从而飞出了合理范围,最终导致算法不收敛(飞到外面那个圆的轨道上,而不可能落到原曲线上)
解决方案:把沿梯度方向的步长限制在某个值内就可以避免'飞出'了,这个方法也叫梯度剪裁.
5.3 激活函数选择总结
尽量选择ReLU函数或者Leakly ReLU函数,相对于Sigmoid/tanh,这两个函数会让梯度更加流畅,训练过程收敛的更快.
6.梯度算法改进
6.1 梯度下降算法存在的问题
全样本梯度下降算法:每算一个导数更新一个权值要所有样本都参与计算,所以速度比较慢
随机梯度下降算法:每次取一个样本当做全部样本来更新梯度,算法的噪声比较多
小批量梯度下降算法:将上面两种方法折中一下选一批训练样本
损失函数特性:一个方向上变化迅速,一个方向上变化缓慢
优化目标:从起点处走到笑脸处(也就是损失要降到0)

L为损失函数,w为权值
在W2方向更陡为震荡方向,而W1方向更加平坦为缓慢前进方向
梯度下降算法存在的问题:山壁之间震荡,往谷低方向前进缓慢,导致在震荡方向做了大量的无用功,而到目标做的功却很少
假如使用加大步长的去解决会发现只是在W2方向震荡的幅度更大了,而W1方向仅仅加了一点点
下面介绍一些常用的方法
6.2 动量法
目标:改进梯度下降算法的问题,即减少震荡,加速通往谷低
改进思想:利用累计历史梯度信息更新梯度,也就是在震荡方向累加,做震荡一次右震荡一次,两次就相互抵消了很多,速度越来越小了,而在行进的W1方向速度就越来越大了->震荡方向抵消,前进方向累加
假如使用加大步长的去解决会发现只是在W2方向震荡的幅度更大了,而W1方向仅仅加了一点点
下面介绍一些常用的方法
6.2 动量法
目标:改进梯度下降算法的问题,即减少震荡,加速通往谷低
改进思想:利用累计历史梯度信息更新梯度,也就是在震荡方向累加,做震荡一次右震荡一次,两次就相互抵消了很多,速度越来越小了,而在行进的W1方向速度就越来越大了->震荡方向抵消,前进方向累加
| 使用动量的小批量梯度下降算法 | 小批量梯度下降算法 |
|---|---|
Require: 学习率 ϵ \epsilon ϵ,动量系数 μ \mu μ Require: 初始参数 θ \theta θ 初始化速度 v = 0 v = 0 v=0 while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 速度更新: v = μ v + ( 1 − μ ) g v = \mu v + (1-\mu)g v=μv+(1−μ)g 4. 更新权值: θ ← θ − ϵ v \theta \leftarrow \theta - \epsilon v θ←θ−ϵv ( μ控制历史梯度是否要衰减) end while |
Require: 学习率 ϵ \epsilon ϵ Require: 初始参数 θ \theta θ while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 更新权值: θ ← θ − ϵ g \theta \leftarrow \theta - \epsilon g θ←θ−ϵg (ϵ是学习率) end while |
其中μ的取值范围[0,1),当μ等于0的时候,等价于梯度下降算法
μ一般不会为1,因为当μ为1的时候就停不下来,会不断累加,而μ只要小于1,那么总会衰减下了
那么动量法还有什么效果?

现象:损失函数常具有不太好的局部最小值或鞍点(高维空间非常常见)
像第一个图最小点并不是在目前的位置而是在更下面
所以梯度下降算法存在这样的问题:局部最小处与鞍点处梯度为0,算法无法通过
W=W-ϵg 当g等于0的时候两次更新的结果是一样的W就收敛不再更新了,所以像原来的那些梯度下降算法都会停在局部最小点或鞍点
而动量法的优势是:由于动量的存在算法可以冲出局部最小点和鞍点,找到更优的点
动量法:V=μv+g,即使g为0了,也有V=μv依然会继续累加,只是会越来越小,但是这样是可以冲出局部最小点和鞍点的,达到最优值
6.3 自适应梯度与RMSProp(靠不同方向取不同的步长来实现)
自适应梯度算法通过减少震荡方向步长增大平坦方向步长来减少震荡,加速通往谷底方向


那么如何区分震荡方向和平坦方向?
答:梯度幅度的平方较大的方向是震荡方向;梯度幅度较小的方向是平坦的方向
AdaGrad方法是一种自适应梯度方法
| AdaGrad | 小批量梯度下降算法 |
|---|---|
Require: 学习率 ϵ \epsilon ϵ,衰减速率 ρ \rho ρ Require: 初始参数 θ \theta θ Require: 小常数 δ \delta δ,用于被小数除时的数值稳定。(通常设为 10 − 5 10^{-5} 10−5) 初始化累积变量 r = 0 r = 0 r=0 while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 累积平方梯度: r ← r + g ∗ g r \leftarrow r + g * g r←r+g∗g 4. 更新权值: w ← w − ϵ r + δ g w \leftarrow w - \frac{\epsilon}{\sqrt{r}+\delta}g w←w−r +δϵg end while |
Require: 学习率 ϵ \epsilon ϵ Require: 初始参数 θ \theta θ while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 更新权值: θ ← θ − ϵ g \theta \leftarrow \theta - \epsilon g θ←θ−ϵg end while |
其中r是用来判断当前值是否是振荡方向,如果历史上r都是很大的那么就是振荡方向
ϵ 1 = ϵ r + δ \epsilon_1 = \frac{\epsilon}{\sqrt{r} + \delta} ϵ1=r +δϵ
ϵ 1 \epsilon_1 ϵ1是更新后的值,在平坦的区域r较小,导致 ϵ 1 \epsilon_1 ϵ1较大,在振荡区域,r较大,则 ϵ 1 \epsilon_1 ϵ1相对较小
但是这样有一个问题,当r不断增大那么 ϵ 1 = ϵ r + δ \epsilon_1 = \frac{\epsilon}{\sqrt{r} + \delta} ϵ1=r +δϵ就会变成一个非常小的值了,这也导致 ϵ \epsilon ϵ失去了调节的作用
优化后:
RMSProp方法是一种自适应梯度方法
| RMSProp | 小批量梯度下降算法 |
|---|---|
Require: 学习率 ϵ \epsilon ϵ,衰减速率 ρ \rho ρ Require: 初始参数 θ \theta θ Require: 小常数 δ \delta δ,用于被小数除时的数值稳定。(通常设为 10 − 5 10^{-5} 10−5) 初始化累积变量 r = 0 r = 0 r=0 while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 累积平方梯度: r ← ρ r + ( 1 − ρ ) g ∗ g r \leftarrow \rho r + (1-\rho)g * g r←ρr+(1−ρ)g∗g 4. 更新权值: w ← w − ϵ r + δ g w \leftarrow w - \frac{\epsilon}{\sqrt{r}+\delta}g w←w−r +δϵg end while |
Require: 学习率 ϵ \epsilon ϵ Require: 初始参数 θ \theta θ while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 更新权值: θ ← θ − ϵ g \theta \leftarrow \theta - \epsilon g θ←θ−ϵg end while |
增加一个ρ作为衰减值,其取值范围是[0,1),当为0的时候仅仅考虑当前梯度的强度,建议设置为0.999
那么加入取的0.999是怎么解决ϵ无限增大的呢?
假如迭代了100次以后,那么100次前的r就是0.999的100次方了,这是一个很小的数了,几乎没有什么影响了,因此只有100次内迭代的r才会有影响
6.4 ADAM(前两种方法的结合)
Adam方法同时使用动量与自适应梯度思想
| Adam算法 | 小批量梯度下降算法 |
|---|---|
Require: 学习率 ϵ \epsilon ϵ,衰减速率 ρ \rho ρ,动量系数 μ \mu μ。(建议值分别为0.999, 0.9) Require: 初始参数 θ \theta θ Require: 小常数 δ \delta δ,用于被小数除时的数值稳定。(通常设为 10 − 5 10^{-5} 10−5) 初始化累积变量 r = 0 , v = 0 r = 0, v = 0 r=0,v=0 while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 累积梯度: v ← μ v + ( 1 − μ ) g v \leftarrow \mu v + (1-\mu)g v←μv+(1−μ)g 4. 累积平方梯度: r ← ρ r + ( 1 − ρ ) g ∗ g r \leftarrow \rho r + (1-\rho)g * g r←ρr+(1−ρ)g∗g 5. 修正偏差: v ~ = v 1 − μ t \tilde{v} = \frac{v}{1-\mu^t} v~=1−μtv; r ~ = r 1 − ρ t \tilde{r} = \frac{r}{1-\rho^t} r~=1−ρtr 6. 更新权值: θ ← θ − ϵ r ~ + δ v ~ \theta \leftarrow \theta - \frac{\epsilon}{\sqrt{\tilde{r}}+\delta}\tilde{v} θ←θ−r~ +δϵv~ end while |
Require: 学习率 ϵ \epsilon ϵ Require: 初始参数 θ \theta θ while 停止标准未满足 do: 1. 从训练集中采样 m m m(批量大小)个样本 { x ( 1 ) , ... , x ( m ) } \{x^{(1)},\dots,x^{(m)}\} {x(1),...,x(m)} 对应的目标为 { y ( 1 ) , ... , y ( m ) } \{y^{(1)},\dots,y^{(m)}\} {y(1),...,y(m)} 2. 计算梯度: g ← 1 m ∇ θ ∑ i L ( f ( x ( i ) ; θ ) , y ( i ) ) g \leftarrow \frac{1}{m}\nabla_{\theta}\sum_i L(f(x^{(i)};\theta),y^{(i)}) g←m1∇θ∑iL(f(x(i);θ),y(i)) 3. 更新权值: θ ← θ − ϵ g \theta \leftarrow \theta - \epsilon g θ←θ−ϵg end while |
其中r是历史梯度平方的累加值,v是历史梯度累加值(建议值分别是0.999和0.9)
修正偏差:这个步骤可以极大的缓解算初期启动很慢的问题
v ~ = v 1 − μ t \tilde{v} = \frac{v}{1-\mu^t} v~=1−μtv中t代表迭代轮次,最开始起动的时候,u是0.9,r和v都是0.

7 .权值初始化

全零初始化:对权值全部初始化为0,网络中不同的神经元有相同的输出,进行相同的参数更新,因此这些神经元学到的参数都一样,等价于一个神经元
建议:避免全零初始化,使用随机初始化


实验结论:初始化时让权值不相等,并不能保证网络能够正常的被训练。
有效的初始化方法:使网络各层的激活值和局部梯度的方差在传播过程中尽量保持一致;以保持网络中正向和反向数据流动。
Xavier初始化
一个神经元,其输入为 z 1 , z 2 , ... , z N z_1,z_2,\dots,z_N z1,z2,...,zN,这 N N N 个输入是独立同分布的;其权值为 w 1 , ... , w N w_1,\dots,w_N w1,...,wN,它们也是独立同分布的,且 w w w 与 z z z 是独立的;其激活函数为 f f f;其最终输出 y y y 的表达式:
y = f ( w 1 ∗ z 1 + ⋯ + w N ∗ z N ) y = f(w_1 * z_1 + \dots + w_N * z_N) y=f(w1∗z1+⋯+wN∗zN)
目标:使网络各层的激活值和局部梯度的方差在传播过程中尽量保持一致,即寻找 w w w 的分布使得输出 y y y 与输入 z z z 的方差一致。
(左侧图示说明:输入 z 1 , z 2 , ... , z N z_1, z_2, \dots, z_N z1,z2,...,zN 经过权值 w 1 , w 2 , ... , w N w_1, w_2, \dots, w_N w1,w2,...,wN 加权求和,再通过激活函数 f f f 得到输出 y y y

目标是希望,Z与Y有相同的分布
y = f ( w 1 ∗ z 1 + ⋯ + w N ∗ z N ) y = f(w_1 * z_1 + \dots + w_N * z_N) y=f(w1∗z1+⋯+wN∗zN)
假设 f f f 为双曲正切函数, w 1 , ... , w N w_1,\dots,w_N w1,...,wN 独立同分布, z 1 , ... , z N z_1,\dots,z_N z1,...,zN 独立同分布,随机变量 w w w 与 z z z 独立,且均值都为 0,则有:
Var ( y ) = Var ( ∑ i = 1 n w i z i ) = ∑ i = 1 n Var ( w i z i ) = ∑ i = 1 n [ [ E ( w i ) ] 2 Var ( z i ) + [ E ( z i ) ] 2 Var ( w i ) + Var ( w i ) Var ( z i ) ] = ∑ i = 1 n Var ( w i ) Var ( z i ) = n Var ( w i ) Var ( z i ) \begin{align*} \text{Var}(y) &= \text{Var}\left( \sum_{i=1}^n w_i z_i \right) = \sum_{i=1}^n \text{Var}(w_i z_i) \\ &= \sum_{i=1}^n \left[ [E(w_i)]^2 \text{Var}(z_i) + [E(z_i)]^2 \text{Var}(w_i) + \text{Var}(w_i)\text{Var}(z_i) \right] \\ &= \sum_{i=1}^n \text{Var}(w_i)\text{Var}(z_i) \\ &= n \text{Var}(w_i)\text{Var}(z_i) \end{align*} Var(y)=Var(i=1∑nwizi)=i=1∑nVar(wizi)=i=1∑n[[E(wi)]2Var(zi)+[E(zi)]2Var(wi)+Var(wi)Var(zi)]=i=1∑nVar(wi)Var(zi)=nVar(wi)Var(zi)
Var ( w ) = 1 N 时, y 的方差与 z 的方差一致。 \text{Var}(w) = \frac{1}{N} \text{ 时,} y \text{ 的方差与 } z \text{ 的方差一致。} Var(w)=N1 时,y 的方差与 z 的方差一致。

- 网络结构:10个隐层,1个输出层,每个隐层包含500个神经元,使用的双曲正切激活函数。
- 随机初始化 :权值采样自 N ( 0 , 1 / N ) \mathcal{N}(0,1/N) N(0,1/N) 的高斯分布, N N N 为输入神经元个数。
- 达到目的 :每层神经元激活值的方差基本相同!

- 网络结构:10个隐层,1个输出层,每个隐层包含500个神经元,使用的ReLU激活函数。
- 随机初始化 :权值采样自 N ( 0 , 1 / N ) \mathcal{N}(0,1/N) N(0,1/N) 的高斯分布, N N N 为输入神经元个数。
- 结论:Xavier初始化方法不太适合ReLU激活函数!

- 网络结构:10个隐层,1个输出层,每个隐层包含500个神经元,使用的ReLU激活函数。
- 随机初始化(He初始化) :权值采样自 N ( 0 , 2 / N ) \mathcal{N}(0,2/N) N(0,2/N) 的高斯分布, N N N 为输入神经元个数。
- 说明:修改了方差项,这是专门针对ReLU激活函数的初始化方法(He初始化)。

权值初始化小结
- 好的初始化方法可以防止前向传播过程中的信息消失,也可以解决反向传递过程中的梯度消失。
- 激活函数选择双曲正切或者Sigmoid时,建议使用Xavier初始化方法;
- 激活函数选择ReLU或Leakly ReLU时,推荐使用He初始化方法。
8.批归一化
上面是调整w使得y与z有相同的分布
而这里是直接对神经元输出进行批归一化

- 小批量梯度下降算法回顾 :每次迭代时会读入一批数据,比如32个样本;经过当前神经元后会有32个输出值 y 1 , ... , y 32 y_1, \dots, y_{32} y1,...,y32。
- 批归一化操作:对这32个输出进行减均值除方差操作;可保证当前神经元的输出值的分布符合0均值1方差。
如果每一层的每个神经元都进行批归一化,就能解决前向传递过程中信号消失的问题.
批归一化操作一般放到全连接后,非线性激活前
批归一化
批归一化算法
- 输入 : B = { x 1 , ... , x m } B = \{x_1, \dots, x_m\} B={x1,...,xm};学习参数: γ , β \gamma, \beta γ,β
- 输出 : { y 1 , ... , y m } \{y_1, \dots, y_m\} {y1,...,ym}
- 计算小批量均值: μ B ← 1 m ∑ i = 1 m x i \mu_B \leftarrow \frac{1}{m}\sum_{i=1}^m x_i μB←m1∑i=1mxi
(说明: x 1 ∼ x m x_1 \sim x_m x1∼xm 的均值) - 计算小批量方差: σ B 2 ← 1 m ∑ i = 1 m ( x i − μ B ) 2 \sigma_B^2 \leftarrow \frac{1}{m}\sum_{i=1}^m (x_i - \mu_B)^2 σB2←m1∑i=1m(xi−μB)2
(说明: x 1 ∼ x m x_1 \sim x_m x1∼xm 的方差) - 归一化: x ^ i ← x i − μ B σ B 2 + ϵ \hat{x}_i \leftarrow \frac{x_i - \mu_B}{\sqrt{\sigma_B^2 + \epsilon}} x^i←σB2+ϵ xi−μB
- 平移缩放: y i ← γ x ^ i + β y_i \leftarrow \gamma \hat{x}_i + \beta yi←γx^i+β
- 前3步已经完成0均值、1方差的标准化
- 第4步是一个优化操作:
- β \beta β:希望将数据映射到新的均值上
- γ \gamma γ:希望将数据映射到新的方差上
- 输出的 y y y 是网络自己选择的均值和方差
问题与解答
-
问题:输出的0均值1方差的正态分布,是最有利于网络分类的分布吗?
- 回答:不一定,前3步完成后并不一定对分类有利;模型会根据对分类的倾向,自行决定数据分布的均值与方差。
-
问题:单张样本测试时,均值和方差怎么设置?
- 回答:均值和方差来自于训练过程中,需要累加训练时每个批次的均值和方差,最后进行平均,用平均后的结果作为预测时的均值和方差。