文章目录
1 池化层
在上篇博客中,有跟大家分析过,在卷积层中没有 padding 的情况下,可以通过调节步长参数
s
\boldsymbol{s}
s 实现特征图的高宽成倍缩小,从而降低了网络的参数量。但是在实际上我们通常使用 Same卷积,即输入和输出特征图的维度一样,这样一来将面临巨大的计算量挑战,而且容易产生过拟合的现象,因此我们需要一种专门的网络层可以实现尺寸缩减功能,它就是这里要介绍的 池化层(pooling layer),通常,池化操作也被称作 下采样。
池化层同样基于局部相关性的思想,通过从局部相关的一组元素中进行采样或信息聚合,从而得到新的元素值。下面介绍两种池化方式:
- 最大池化(Max Pooling):选择 pooling 窗口中的最大值作为采样值;
- 均值池化(Mean Pooling):将 pooling 窗口中的所有值相加取平均, 以平均值作为采样值。
不管采用什么样的池化函数,当输入作出少量平移时,池化能够帮助输入的表示近似 不变(invariant),对于平移的不变性是指当我们对输入进行少量平移时,经过池化函数后的大多数输出并不会发生改变。池化操作就是图像的 resize,平时一张狗的图像被缩小了一倍我们还能认出这是一张狗的照片,这说明这张图像中仍保留着狗最重要的特征,我们一看就能判断图像中画的是一只狗,图像压缩时去掉的信息只是一些无关紧要的信息,而留下的信息则是具有尺度不变性的特征,是最能表达图像的特征。说明池化能够提升模型的尺度不变性、旋转不变性。
以
5
×
5
\boldsymbol{5 × 5}
5×5 输入
X
\boldsymbol{X}
X 的最大池化层为例,考虑池化窗口大小
k
=
2
\boldsymbol{ k =2}
k=2 ,步长
s
=
2
\boldsymbol{s = 2}
s=2 的情况。
绿色虚线方框代表第一次池化窗口的位置,感受野元素集合为:
{
1
,
−
1
,
−
1
,
−
2
}
\boldsymbol{\{ 1, -1, -1,-2\}}
{1,−1,−1,−2}
在最大池化采样的方法下,通过:
x
′
=
m
a
x
(
{
1
,
−
1
,
−
1
,
−
2
}
)
=
1
\boldsymbol{x' = } \boldsymbol{\ max(\{ 1, -1, -1,-2\}) = 1}
x′= max({1,−1,−1,−2})=1
计算出当前位置的输出值为 1,并写入对应位置。若采用的是平均池化操作,则此时的输出值应为:
x
′
=
a
v
g
(
{
1
,
−
1
,
−
1
,
−
2
}
)
=
−
0.75
\boldsymbol{x' = } \boldsymbol{\ avg(\{ 1, -1, -1,-2\}) = -0.75}
x′= avg({1,−1,−1,−2})=−0.75
计算完当前位置的池化窗口后,与卷积层的计算步骤类似,将池化窗口按着步长向右移动若干单位,到达上图中就是实现绿色窗口所在位置此时的输出为:
x
′
=
m
a
x
(
{
−
1
,
0
,
−
2
,
2
}
)
=
2
\boldsymbol{x' = } \boldsymbol{\ max(\{ -1, 0, -2,2\}) = 2}
x′= max({−1,0,−2,2})=2
同样的方法,逐渐移动感受野窗口至最右边,计算出输出
x
′
=
m
a
x
(
{
2
,
0
,
3
,
1
}
)
=
3
\boldsymbol{x' = } \boldsymbol{\ max(\{ 2,0, 3,1\}) = 3}
x′= max({2,0,3,1})=3 此时窗口已经到达输入边缘,按照卷积层同样的方式,感受野窗口向下移动一个步长,并回到行首。
循环往复,直至最下方、最右边,获得最大池化层的输出,长宽为 4 × 4 \boldsymbol{4 × 4} 4×4,小于输入 X \boldsymbol{X} X 的高宽。
池化层没有需要学习的参数,计算简单,在 CNN 中可用来减小尺寸,提高运算速度及减小噪声影响,让各特征更具有健壮性。池化层比卷积层更简单,它没有卷积运算,只是在滤 波器算子滑动区域内取最大值或平均值。而池化的作用则体现在降采样:保留显著特征、降低特征维度,增大感受野。深度网络越往后面越能捕捉到物体的语义信息,这种语义信息是建立在较大的感受野基础上。
通过设计池化层感受野的高宽𝑘和步长
s
\boldsymbol{s}
s 参数,可以实现各种降维运算。比如,一种常用的池化层设定是池化窗口大小
k
=
2
\boldsymbol{k = 2}
k=2,步长
s
=
2
\boldsymbol{s = 2}
s=2,这样可以实现输出只有输入高宽一半的目的。如下图中,池化窗口
k
=
3
\boldsymbol{k = 3}
k=3,步长
s
=
2
\boldsymbol{s = 2}
s=2,输入
X
\boldsymbol{X}
X 高宽为
5
×
5
\boldsymbol{5×5}
5×5,输出
O
\boldsymbol{O}
O 高宽只有
2
×
2
\boldsymbol{2×2}
2×2。
2 BatchNorm层
卷积神经网络的出现,网络参数量大大减低,使得几十层的深层网络成为可能。然而,在残差网络出现之前,网络的加深使得网络训练变得非常不稳定,甚至出现网络长时间不更新甚至不收敛的现象,同时网络对超参数比较敏感,超参数的微量扰动也会导致网络的训练轨迹完全改变。
2015 年,Google 研究人员 Sergey Ioffe 等提出了一种参数标准化(Normalize)的手段,并基于参数标准化设计了 Batch Nomalization(简写为 BatchNorm,或 BN)层 。BN 层的提出,使得网络的超参数的设定更加自由,比如更大的学习率、更随意的网络初始化等,同时网络的收敛速度更快,性能也更好。BN 层提出后便广泛地应用在各种深度网络模型上,卷积层、BN 层、ReLU 层、池化层一度成为网络模型的标配单元块,通过堆叠 Conv-BN-ReLU-Pooling 方式往往可以获得不错的模型性能。总结 BN 层的作用如下三点,在后面过程中会具体怎么实现中这些作用的。
- 加快网络的训练和收敛的速度;
- 控制梯度爆炸防止梯度消失;
- 防止过拟合。
为什么需要对网络中的数据进行标准化操作?我们可以先来看看虑 Sigmoid 激活函数和它的梯度分布。
由上图知,Sigmoid 函数在
𝑥
∈
[
−
2
,
2
]
\boldsymbol{𝑥 ∈ [−2 ,2]}
x∈[−2,2] 区间的导数值在
[
0.1
,
0.25
]
\boldsymbol{[0.1,0.25]}
[0.1,0.25] 区间分布;
𝑥
>
2
\boldsymbol{𝑥 > 2}
x>2 或
𝑥
<
−
2
\boldsymbol{𝑥 <-2}
x<−2 时,Sigmoid 函数的导数变得很小,逼近于 0,在反向传播中从而容易出现梯度弥散现象。为了避免因为输入较大或者较小而导致 Sigmoid 函数出现梯度弥散现象。如假设网络中每层的学习梯度都小于最大值
0.25
\boldsymbol{0.25}
0.25,网络中有
n
\boldsymbol{n}
n 层,因为链式求导的原因,第一层的梯度将会小于
0.25
\boldsymbol{0.25}
0.25 的
n
\boldsymbol{n}
n 次方,所以学习速率相对来说会变的很慢,而对于网络的最后一层只需要对自身求导一次,梯度就大,学习速率就会比较快,这就会造成在一个很深的网络中,浅层基本不学习,权值变化小,而后面几层网络一直学习,后面的网络基本可以表征整个网络,这样失去了深度的意义。因此将函数输入
𝑥
\boldsymbol{𝑥 }
x 标准化映射到 0 附近的一段较小区间将变得非常重要,上图中,通过标准化重映射后,值被映射在 0 附近,此处的导数值不至于过小,从而不容易出现梯度弥散现象。同时,假如激活层斜率均为最大值
0.25
\boldsymbol{0.25}
0.25,所有层的权值为 100,这样梯度就会指数增加,但是如果进行了归一化之后,权值就不会很大,梯度爆炸的情况就会减少。
再来分析以下只有 2 个输入节点的线性模型:
L
=
a
=
x
1
w
1
+
x
2
w
2
+
b
\boldsymbol{L = a= x_1w_1 + x_2w_2+b}
L=a=x1w1+x2w2+b:
由于模型相对简单,可以绘制出 2 种 x 1 , x 2 \boldsymbol{x_1,x_2} x1,x2 下的函数的损失等高线图:
其中,左边的损失等高线图是
x
1
∈
[
1
,
10
]
,
x
2
∈
[
100
,
1000
]
\boldsymbol{x_1∈[1,10],x_2∈[100,1000]}
x1∈[1,10],x2∈[100,1000] 时的某条优化轨迹线示意图,右边的损失等高线图是
x
1
∈
[
1
,
10
]
,
x
2
∈
[
1
,
10
]
\boldsymbol{x_1∈[1,10],x_2∈[1,10]}
x1∈[1,10],x2∈[1,10] 时的某条优化轨迹线示意图,图中的圆环中心即为全局极值点。当
x
1
,
x
2
\boldsymbol{x_1,x_2}
x1,x2 输入分布相近时,
∂
L
w
1
,
∂
L
w
2
\boldsymbol{\frac{\partial L}{w_1},\frac{\partial L}{w_2}}
w1∂L,w2∂L 偏导数值相当,收敛更加快速,优化轨迹更理想如上图中的右图;当
x
1
,
x
2
\boldsymbol{x_1,x_2}
x1,x2 输入分布差距较大时,比如
x
1
≪
x
2
\boldsymbol{x_1≪x_2}
x1≪x2,则
∂
L
w
1
≪
∂
L
w
2
\boldsymbol{\frac{\partial L}{w_1}≪\frac{\partial L}{w_2}}
w1∂L≪w2∂L,损失函数等势线在
x
2
\boldsymbol{x_2}
x2 轴更加陡峭,某条可能的优化轨迹如上图中的左图。
通过上述的 2 个例子,能够知道网络层输入
x
\boldsymbol{x}
x 分布相近,并且分布在较小范围内时(如 0 附近),更有利于函数的优化。我们可以通过数据标准化操作达到这个目的,通过数据标准化操作可以将数据
x
\boldsymbol{x}
x 映射到
x
^
\boldsymbol{\hat{x}}
x^:
x
^
=
x
−
μ
r
σ
r
2
+
ϵ
\boldsymbol{\hat{x}}= \boldsymbol{\frac{x - \mu_r}{\sqrt{\sigma_r^2+\epsilon}}}
x^=σr2+ϵx−μr
其中
μ
r
、
σ
r
2
\boldsymbol{\mu_r、\sigma_r^2}
μr、σr2 来自统计的所有数据的均值和方差,
ϵ
\boldsymbol{\epsilon}
ϵ 是为防止出现除 0 错误而设置的较小数,如 1e − 8。在基于 Batch 的训练阶段,考虑 Batch 内部的均值
μ
B
\boldsymbol{\mu_B}
μB 和方差
σ
B
2
\boldsymbol{\sigma_B^2}
σB2:
μ
B
=
1
m
∑
i
=
1
m
x
i
σ
B
2
=
1
m
∑
i
=
1
m
(
x
i
−
μ
B
)
2
\boldsymbol{\mu_B} = \boldsymbol{\frac{1}{m}\sum_{i = 1}^{m}x_i} \\ \boldsymbol{\sigma_B^2} = \boldsymbol{\frac{1}{m}\sum_{i = 1}^{m}(x_i - \mu_B)^2}
μB=m1i=1∑mxiσB2=m1i=1∑m(xi−μB)2
其中 m 为 Batch 样本数,而且因为每次网络都是随机取 Batch,这样就会使得整个网络不会朝这一个方向使劲学习。一定程度上避免了过拟合。。因此,在训练阶段,通过:
x
^
t
r
a
i
n
=
x
t
r
a
i
n
−
μ
B
σ
B
2
+
ϵ
\boldsymbol{\hat{x}_{train}}= \boldsymbol{\frac{x_{train} - \mu_B}{\sqrt{\sigma_B^2+\epsilon}}}
x^train=σB2+ϵxtrain−μB
标准化输入,并记录每个 Batch 的统计数据
μ
B
、
σ
B
2
\boldsymbol{\mu_B、\sigma_B^2}
μB、σB2,用于统计真实的全局
μ
r
、
σ
r
2
\boldsymbol{\mu_r、\sigma_r^2}
μr、σr2。在测试阶段,根据记录的每个 Batch 的
μ
B
、
σ
B
2
\boldsymbol{\mu_B、\sigma_B^2}
μB、σB2 估计出的所有训练数据的
μ
r
、
σ
r
2
\boldsymbol{\mu_r、\sigma_r^2}
μr、σr2,依据:
x
^
t
e
s
t
=
x
t
e
s
t
−
μ
r
σ
r
2
+
ϵ
\boldsymbol{\hat{x}_{test}}= \boldsymbol{\frac{x_{test} - \mu_r}{\sqrt{\sigma_r^2+\epsilon}}}
x^test=σr2+ϵxtest−μr
将每层的输入标准化。上述的标准化运算并没有引入额外的待优化变量,各个均值和方差均由统计得到,不需要参与梯度更新。但实际上,为了提高 BN 层的表达能力,BN 层作者引入了 “scale and shift” 技巧,将
x
^
\boldsymbol{\hat{x}}
x^ 变量再次映射变换:
x
~
=
x
^
⋅
γ
+
β
\boldsymbol{\tilde{x} = \hat{x} \cdot\gamma + \beta}
x~=x^⋅γ+β
其中
γ
\boldsymbol{\gamma}
γ 参数实现对标准化后的
x
^
\boldsymbol{\hat{x}}
x^ 再次进行缩放,
β
\boldsymbol{\beta}
β 参数实现对标准化的
x
^
\boldsymbol{\hat{x}}
x^ 进行平移,不同的是,
γ
、
β
\boldsymbol{\gamma、\beta}
γ、β 参数均由反向传播算法自动优化即学习参数,实现网络层“按需”缩放平移数据的分布的目的。综上,BN 层的流程如下:
原文的算法流程如下:
最后来分析一下 BN 层中的参数共享问题,我在上一篇博客中跟大家分享过,特征图的数量取决于卷积层中的卷积核个数。1 个卷积核产生 1 个 feature map,1 个 feature map 有 1 对
γ
\boldsymbol{\gamma}
γ 和
β
\boldsymbol{\beta}
β 参数,同一 Batch 同 channel 的 feature map 共享同一对
γ
\boldsymbol{\gamma}
γ 和
β
\boldsymbol{\beta}
β 参数,若卷积层有
n
\boldsymbol{n}
n 个卷积核,则有
n
\boldsymbol{n}
n 对
γ
\boldsymbol{\gamma}
γ 和
β
\boldsymbol{\beta}
β 参数。
至此,我跟大家介绍完了卷积神经网络的基础网络结构,分了两篇博客,分别讲了卷积层、池化层和 BN 层,在下一篇博客中我会跟大家介绍几种经典的 CNN 模型。期待您的访问!感恩!