推荐在我的博客中给我留言,这样我会随时收到你的评论,并作出回复。
在上一篇神经网络的Python实现(二)全连接网络中,已经介绍了神经网络的部分激活函数,损失函数和全连接网络的前馈和反向传播公式及Numpy实现。这篇博文将要详细介绍卷积神经网络的概念,并且进行前馈和反向传播的公式推导及Numpy实现。
卷积神经网络
卷积神经网络(Convolutional Neural Network)非常擅于处理图像任务,它的灵感来自于视觉神经中的感受野
这一概念,卷积神经网络的卷积核(Convolution Kernel) 好似感受野一样去扫描数据。一个卷积神经网络基本包括卷积层、池化层和输出层。
接下来介绍什么是卷积核、卷积神经网络中的卷积是怎么运算的。
卷积和卷积核
卷积神经网络中的卷积操作与数学中的类似。就是输入数据中不同数据窗口的数据和卷积核(一个权值矩阵)作内积的操作。其中卷积核是卷积神经网络中卷积层的最重要的部分。卷积核相当于信息处理中的滤波器,可以提取输入数据的当前特征。卷积核的实质是一个权值矩阵,在下图中的卷积核便是一个权值如下的矩阵(图中黄色色块中的红色数字)
[ 1 0 1 0 1 0 1 0 1 ] \left[ \begin{matrix} 1 & 0 & 1\\ 0 & 1 & 0\\ 1 & 0 & 1 \end{matrix} \right] ⎣⎡101010101⎦⎤
如果并不理解卷积,那么我们来看图中输出的第一行第一列的4是怎么得到的。
原输入数据大小为 5 × 5 5\times 5 5×5,我们要使用 3 × 3 3\times3 3×3的卷积核来进行卷积,我们使用 ∗ \ast ∗表示卷积操作。那么图中第一个4的运算过程就可以表达为:
[ 1 1 1 0 1 1 0 0 1 ] ∗ [ 1 0 1 0 1 0 1 0 1 ] = 1 × 1 + 1 × 0 + 1 × 1 + 0 × 0 + 1 × 1 + 1 × 0 + 0 × 1 + 0 × 0 + 1 × 1 = 4 \left[ \begin{matrix} \color{red}{1} & 1 & 1\\ 0 & 1 & 1\\ 0 & 0 & 1 \end{matrix} \right] * \left[ \begin{matrix} \color{blue}{1} & 0 & 1\\ 0 & 1 & 0\\ 1 & 0 & 1 \end{matrix} \right]= \color{red}{1}\times\color{blue}{1} + 1\times0+1 \times 1+ 0\times0+1\times1+1\times0+ 0\times1+0\times0 +1\times1=4 ⎣⎡100110111⎦⎤∗⎣⎡101010101⎦⎤=1×1+1×0+1×1+0×0+1×1+1×0+0×1+0×0+1×1=4
剩下位置的输出就是卷积核在输入矩阵上从左到右从上到下移动一格做如上卷积操作过程的结果。
步长(strides)和填充(padding)
上面例子说到的一格表示的就是步长(strides),步长分为横向步长和纵向步长,步长是多少就表示一次卷积操作之后卷积核移动的距离。知道步长的概念了,我们就可以去计算一下根据输入大小,卷积核大小,我们得到的输出的大小。假设用 C C C表示边长,那么:
C o u t p u t = C i n p u t − C k e r n e l s t r i d e s + 1 C_{output} = \frac{C_{input}-C_{kernel}}{strides}+1 Coutput=stridesCinput−Ckernel+1
根据公式当步长为1或是输入大小能够被步长整除时很好处理,无法整除时也就是卷积核移动到最后,输入数据的剩下的部分不足卷积核大小,这时我们会想到要么将输入变大点让它能够整除要么是干脆边界直接丢弃让它能够整除。这两种处理办法对应于填充(padding) 的两种方式,‘SAME’和’VALID’。
VALID
O w = c e i l ( I w − k w + 1 s w ) O h = c e i l ( I h − k h + 1 s h ) O_w = ceil\left(\frac{I_w-k_w+1}{s_w}\right)\\ O_h = ceil\left(\frac{I_h-k_h+1}{s_h}\right)\\ Ow=ceil(swIw−kw+1)Oh=ceil(shIh−kh+1)
其中 c e i l ceil ceil为向上取整, w w w是宽方向, h h h是长方向, I , O , k , s I,O,k,s I,O,k,s分别代表输入、输出、卷积核和步长。
超过 O w , O h O_w,O_h Ow,Oh部分就舍弃不要了。
真正输入大小 I w = s w ( O w − 1 ) + k w I h = s h ( O h − 1 ) + k h I_w = s_w(O_w-1)+k_w\\I_h = s_h(O_h-1)+k_h Iw=sw(Ow−1)+kwIh=sh(Oh−1)+kh
SAME
SAME就是在输入周围补0,我们先计算补0后的输出大小:
O w = c e i l ( I w s w ) O h = c e i l ( I h s h ) O_w = ceil\left(\frac{I_w}{s_w}\right)\\ O_h = ceil\left(\frac{I_h}{s_h}\right) Ow=ceil(swIw)Oh=ceil(shIh)
接下来便根据应得到输出的大小去padding。
P h = max ( ( O h − 1 ) × s h + k h − I h , 0 ) P w = max ( ( O w − 1 ) × s w + k w − I w , 0 ) P t o p = f l o o r ( P h 2 ) P b o t t o m = P h − P t o p P l e f t = f l o o r ( P w 2 ) P r i g h t = P w − P l e f t \begin{aligned} P_h &= \max \left((O_h-1)\times s_h + k_h-I_h\ \ ,\ 0\right)\\ P_w &= \max \left((O_w-1)\times s_w + k_w-I_w\ \ ,\ 0\right)\\ P_{top} &= floor\left(\frac{P_h}{2}\right) \ \ \ \ \ \ \ \ P_{bottom} = P_h - P_{top} \\ P_{left} &= floor\left(\frac{P_w}{2}\right) \ \ \ \ \ \ \ \ P_{right} = P_w - P_{left} \end{aligned} PhPwPtopPleft=max((Oh−1)×sh+kh−Ih , 0)=max((Ow−1)×sw+kw−Iw , 0)=floor(2Ph) Pbottom=Ph−Ptop=floor(2Pw) Pright=Pw−Pleft
其中 f l o o r floor floor 是向下取整。
这样0就几乎对称地分布在输入四周。
多通道的卷积
一般卷积神经网络处理的都是3通道或是多通道的图像数据,那么对于多通道如何卷积呢?对于多通道,卷积公式并不变,只是要求卷积核通道与输入通道数一致,不同通道分别做内积,然后不同通道得到的值相加起来作为最后的输出。如图。
对于计算,我们使用 2 × 2 × 2 2\times2\times2 2×2×2的输入和 2 × 2 × 2 2\times2\times2 2×2×2的卷积核举个例子:
[ [ 1 2 3 4 ] , [ 5 6 7 8 ] ] ∗ [ [ 1 2 3 4 ] , [ 5 6 7 8 ] ] = [ 1 × 1 + 5 × 5 2 × 2 + 6 × 6 3 × 3 + 7 × 7 4 × 4 + 8 × 8 ] = [ 26 40 58 80 ] \begin{aligned} &\ \ \ \ \left[ \begin{matrix} \left[ \begin{matrix} 1 & 2\\ 3 & 4 \end{matrix} \right], \left[ \begin{matrix} 5 & 6\\ 7 & 8 \end{matrix} \right] \end{matrix} \right] *\left[ \begin{matrix} \left[ \begin{matrix} 1 & 2\\ 3 & 4 \end{matrix} \right], \left[ \begin{matrix} 5 & 6\\ 7 & 8 \end{matrix} \right] \end{matrix} \right] \\ \\ &=\left[ \begin{matrix} 1\times1+5\times5 & 2 \times 2+6 \times 6 \\ 3\times3+7\times7 & 4 \times4+8\times8 \end{matrix} \right]\\ \\ &=\left[ \begin{matrix} 26 & 40\\ 58 & 80 \end{matrix} \right] \end{aligned} [[1324