卷积神经网络 Convolutional Neural Networks,CNN

卷积神经网络(CNN)在普通神经网络的基础上将隐藏层分为了卷积层、池化层、全连接层的结构;

通常为一个或多个卷积层后接一个池化层,如此重复多次后,最后接两至三个全连接层;

如图为卷积神经网络鼻祖LeNet(1998年)的网络结构:

卷积层 Convolutional Layer

作用: 获取图像特征

行为:通过一定大小的卷积核(矩阵)对图像逐步做运算,得到一个新的数据矩阵;

进行卷积层运算后,除特殊说明外都会紧接着进行激活函数的运算,激活函数的介绍见上文。

也有将激活函数单独称为激活层的说法。

卷积层涉及的相关概念如下:

卷积核 Conv kernel

卷积核即一个小的矩阵,通常为1*1、3*3、5*5等尺寸,其角色相当于普通神经网络的 权值 ,作用类似于一个有着特定功能的滤波器,原图像经过卷积核运算后可以得到这个图像的特征图谱;

不同的卷积核可以获取到不同的局部特征,如下图的例子:

步长 stride

步长即卷积运算时,卷积核每次移动的距离;

步长会影响卷积运算的输出矩阵的大小。

填充 padding

无论使用何种步长,输入矩阵经过卷积运算后,尺寸都会变小;

为了使输出矩阵尺寸与输入尺寸一致/或是防止输出矩阵尺寸变得太小,可以选择在计算前先在输入矩阵周围进行补零填充。

感受野 Receptive Field

卷积神经网络的每一层都会计算得到一系列特征图(feature map),这些特征图又会作为下一层的输入;

感受野即这些特征图对应到 输入图片的区域大小

感受野越大,即表明得到的特征图所利用的信息越是全局的,而不仅仅是局部信息。

相关名词:视野(field of view,FOV)

多输入通道、多输出通道和批量操作

多输入通道场景:例如RGB图片包含3个通道,灰度图包含1个通道,又称图片深度。

多输入通道的卷积核仍称为 一个 卷积核; 以RGB为例,第一层多通道输入后经过卷积计算会把3个通道的结果合并得到一个输出通道。

多输出通道场景:单个卷积核只能提取特定的图像特征,因此通常使用多个卷积核同时提取,即会得到多个输出;(通常将卷积核的 输出通道数 叫做卷积核的 个数 

批量操作:将多个样本放在一起形成一个mini-batch进行批量操作

池化层 Pooling Layer

作用:

  1. 降维:池化后一个像素对应前一层的一个区域
  2. 抽象:提取背景/纹理
  3. 减少计算量:池化层减少了特征图的变量个数

行为:预先设定一个矩阵框大小,对输入矩阵逐步计算;

  1. 平均池化(average-pooling/mean-pooling):计算方法为矩阵框大小内的元素取均值作为输出;
  2. 最大值池化(max-pooling):计算方法为矩阵框大小内的元素取最大值作为输出;

意义:

卷积层的操作会引入一定的误差,该误差来自于两方面:(1)邻域大小受限造成的估计值方差增大;(2)卷积层参数误差造成估计均值的偏移;

平均池化能减小第一种误差,更多的 保留图像的背景信息

最大值池化能减小第二种误差,更多的 保留纹理信息

池化层不包含需要学习的参数。使用时仅需指定类型(mean-pooling/max-pooling)、核大小(kernel size)和步长(stride)等超参数。

在神经网络训练的反向传播过程中,池化层将误差项直接传递到上一层,而没有梯度的计算:

        对于最大值池化,下一层的误差项的值会原封不动的传递到上一层对应区块中的最大值所对应的神经元,而其他神经元的误差项的值都是0;

        对于平均池化,下一层的误差项的值会平均分配到上一层对应区块中的所有神经元。

全连接层 Fully Connected Layer

作用: 分类

全连接层实际上就是传统的神经网络,每一神经元与输出层的神经元通过权值相连。当全连接层输入的数据是二维或三维矩阵矩阵时,需要拉伸成一维的列表运算;

最后一层全连接层的神经元个数与类别总数相等,如手写数字即0-9共10个类别;

全连接层后面一般会进行softmax激活运算,将每个神经元的值转换成概率的表示,见下图例子;也有将softmax激活操作称为输出层的说法。

CNN计算过程中的尺寸变化

CNN计算过程中的尺寸变化与卷积核个数、卷积核大小、卷积步长、卷积填充大小有关。

输入通道数为n,输出通道数为1:

输入通道数为n,输出通道数为m:

以图中为例,此场景中,输入为8*8,输入为3个通道,也可表示为8*8*3;

使用3*3*3的卷积核,共5个(kernel1~kernel5),步长为1,不填充;

计算时,以kernel1为例,输入的3通道经一次卷积后变为单通道,输入大小8*8经一次卷积后变为6*6;

因使用了5个卷积核,所以输出即6*6*5,注意输出尺寸的第三个参数为卷积核个数,而输入尺寸的第三个参数为图片深度。

结合具体的神经网络的例子来看一下CNN计算过程中的尺寸变化:(注意图中标的尺寸黑色字体为卷积后的尺寸,红色字体为池化后的尺寸,亦可通过薄厚来区分)

此例中,输入为224*224*3,即图片大小224*224,深度为3;

1)前两次的卷积操作为:64个3*3卷积核,控制步长与填充使大小不变,得到输出224*224*64;

2)经一次池化层降维,通道数不变,尺寸变小,得到输出112*112*64;

3)卷积两次:128个3*3卷积核,控制步长与填充使大小不变,得到输出112*112*128;

4)池化一次,得到输出56*56*128;

5)…

6)最后一次池化,得到7*7*512。

CNN计算过程中的梯度消失与梯度爆炸

深度神经网络训练的时候,采用的是反向传播方式,该方式使用链式求导,计算每层梯度的时候会涉及一些连乘操作,因此如果网络过深:

  • 那么如果连乘的因子大部分小于1,最后乘积的结果可能趋于0,也就是 梯度消失 ,后面的网络层的参数不发生变化;
  • 那么如果连乘的因子大部分大于1,最后乘积可能趋于无穷,这就是 梯度爆炸 。

CNN计算过程中的参数量、计算量、内存占用

参数量

卷积核:设Nin, Nout, K分别表示in_channels,out_channels,和kernel_size,则参数量为:Nin*K*K*Nout(权重部分) + Nout(偏置部分)

BN层:2*Nin

全连接层:Lin*Lout + Lout(设Lin,Lout分别表示输入和输出向量的长度)

常用网络架构的参数数量:

  • AlexNet:62369155

  • VGG16:138357544

  • ResNet10(BasicBlock):14356544

  • ResNet18(BasicBlock):33161024

  • ResNet34(BasicBlock):63470656

  • ResNet50(Bottleneck):46159168

  • ResNet101(Bottleneck):85205312

  • ResNet152(Bottleneck):117364032

计算量

一次卷积操作的计算量ConvOnce = Nin*(K*K+K*K-1) + (Nin-1),其中,卷积的乘法为K*K,卷积核的加法K*K-1,Nin-1为跨通道的加法数

设输入分辨率为Hin*Win,经过卷积后输出分辨率为Hout*Wout,

Hout = [Hin+2*padding[0]-dilation[0]*(kernel_size[0]-1)-1]/stride[0]+1

Wout = [Win+2*padding[1]-dilation[1]*(kernel_size[1]-1)-1]/stride[1]+1

结合输出通道数Nout和Batch数B,可得卷积的计算量为:B*Nout*Hout*Wout*ConvOnce

计算量相关指标:

模型计算量需求-FLOPs(floating-point operations,即进行多少次浮点运算)

平台算力-FLOPS(floating-point operations per second,即单位时间)

帧率需求fps

三者之间关系:FLOPs= FLOPS/fps

MACs, MAdds:乘加累积操作数(Multiply–Accumulate Operations),包含一个乘法操作与一个加法操作,大约包含2FLOPs。

内存占用

占用memory的网络要素包括:

  • 各层的feature map(占用主要的memory)

  • 网络的权重(根据float32占用4bytes可以折算上面的权重所占用的memory)

  • 训练过程需要在考虑梯度占用内存

Logo

欢迎加入我们的广州开发者社区,与优秀的开发者共同成长!

更多推荐