CNN的反向传播过程的推导(池化层、卷积层)

上一篇文章介绍了DNN的反向传播,对DNN不清楚的可以去看看,CNN在DNN的基础上进行解释。

一、回顾DNN的反向传播

上一篇DNN反向传播过程得出结论:

1、计算每一层的W、b的梯度,需要计算出\frac{\partial J}{\partial z^l}

2、然后每一层的W的梯度和b的梯度

                                                       \frac{\partial J}{\partial W^l}=\frac{\partial J}{\partial z^l}(a^{l-1})^T

                                                      \frac{\partial J}{\partial b^l}=\frac{\partial J}{\partial z^l}

3、第l层的\frac{\partial J}{\partial z^l}和网络后一层的\frac{\partial J}{\partial z^{l+1}}存在下面的递推关系

                                                       \frac{\partial J}{\partial z^l}=\frac{\partial J}{\partial z^{l+1}}\frac{\partial z^{l+1}}{\partial z^l}=(W^{L+1})^T\frac{\partial J}{\partial z^{l+1}}\sigma^{'}(z^l)

4、有了W、b梯度表达式,就可以用梯度下降法来优化W、b,知道求出最终的W、b的值。

二、CNN的反向传播过程

CNN直接使用DNN的反向传播过程,有几个问题需要解决:

1、池化层没有激活函数,相当于激活函数为线性激活函数\sigma(z)=z 。这样激活函数的导数为1;

2、池化层在前向传播的过程中,对输入进行了压缩,那我们向前反向传播推导\frac{\partial J}{\partial z^{l-1}},这个推导过程和DNN完全不同;

3、卷积层是通过张量卷积,或者说若干个矩阵卷积求和而得的当前层的输出,这和DNN很不相同,DNN的全连接层是直接进行矩阵乘法得到当前层的输出。这样在卷积层反向传播的时候,上一层的\frac{\partial J}{\partial z^{l-1}}递推计算方法肯定有所不同。

4、对于卷积层,由于W使用的运算是卷积,那么从\frac{\partial J}{\partial z^{l}}推导出该层的所有卷积核的W,b的方式也不同。

问题1是比较容易解决的,问题2、3、4是解决CNN反向传播的关键。下面的研究过程中,由于卷积层存在多个卷积核,各个卷积核的处理方式是完全相同且独立的。为了简化算法公式的复杂度,我们下面提到的卷积核都是卷积层中若干卷积核中的一个。

三、已知池化层的\frac{\partial J}{\partial z^{l}},求出上一隐藏层的\frac{\partial J}{\partial z^{l-1}}

在前向传播过程中,池化层一般会使用Max或Average对输入进行池化,池化的区域大小给定。现在我们要从缩小区域后的\frac{\partial J}{\partial z^{l}}还原之前较大区域对应的误差\frac{\partial J}{\partial z^{l-1}}

在反向传播时,我们首先会把δlδl的所有子矩阵矩阵大小还原成池化之前的大小,然后如果是MAX,则把δlδl的所有子矩阵的各个池化局域的值放在之前做前向传播算法得到最大值的位置。如果是Average,则把δlδl的所有子矩阵的各个池化局域的值取平均后放在还原后的子矩阵位置。这个过程一般叫做upsample。

用一个例子可以很方便的表示:假设我们的池化区域大小是2x2。\frac{\partial J}{\partial z^{l}}的第k个子矩阵为:

                                                                               \frac{\partial J}{\partial z^{l,k}}=\begin{pmatrix} 4 & 8\\ 6 & 2 \end{pmatrix}

如果池化区域大小为2*2,我们先将\frac{\partial J}{\partial z^{l}}还原,即变成:

1)如果是MAX,假设我们之前在前向传播时记录的最大值位置分别是左上,右下,右上,左下,则转换后的矩阵为:

                                                                          \begin{pmatrix} 4 & 0 &0 &0 \\ 0 & 0 & 0& 8\\ 0& 6 &0 &0 \\ 0& 0& 2 & 0 \end{pmatrix}

2) 如果是Average,则进行平均:转换后的矩阵为:

                                                                       \begin{pmatrix} 1 & 1 &2 & 2\\ 1 &1 & 2& 2\\ 1.5& 1.5 &0.5 &0.5 \\ 1.5& 1.5& 0.5 & 0.5 \end{pmatrix}

3)这样我们就得到了卷积层后一层upsample后的\frac{\partial J}{\partial z^{l}},由于池化层没有W、b参数需要学习,是一个分辨率变化过程,使用的是线性激活函数。所以

                                                                \frac{\partial J}{\partial z^{l-1}}=upsample(\frac{\partial J}{\partial z^{l}}).\sigma^{'}(z^{l-1})

结论:由池化层的结果向前一层传播的话,由于池化层没有参数需要学习,但是由于池化操作造成了数据维度的变化,所以需要有一个数据的上采样过程,上采样过程跟池化的方法有关。上采样之后,由于池化是个线性函数的过程,所以要求针对上一层的z的梯度,中间只有一个上一层的z到a的激活函数,因此得出上面的结论。

四、已知卷积层的\frac{\partial J}{\partial z^{l}},求出上一隐藏层的\frac{\partial J}{\partial z^{l-1}}

我们首先写出卷积层的前向传播过程公式,假设a^{l-1}为卷积层前的输入数据,a^{l}为经过一个卷积核和激活函数的操作结果

                                                                    a^{l}=\sigma(z^{l})=\sigma(a^{l-1}*W^{l}+b^l)

我们以一个l-1层为3*3的矩阵为例,卷积核W^l为2*2,滑动步伐为1,则输出为2*2的矩阵。简化b^l为0,左侧为l-1层,右侧为l层

                                                    \begin{pmatrix} a_{11} &a_{12} &a_{13} \\ a_{21}&a_{22} &a_{23} \\ a_{31} &a_{32} & a_{33} \end{pmatrix}*\begin{pmatrix} w_{11} &w_{12} \\ w_{21} & w_{22} \end{pmatrix}=\begin{pmatrix} z_{11} & z_{12}\\ z_{21} & z_{22} \end{pmatrix} 

                                                                  \sigma(\begin{pmatrix} z_{11} & z_{12}\\ z_{21} & z_{22} \end{pmatrix})=\begin{pmatrix} a_{11} & a_{12}\\ a_{21} & a_{22} \end{pmatrix}

首先我们从前面的DNN可以得出求解对于W和b的梯度变化,求该层 的\frac{\partial J}{\partial z^{l}}是关键的,而且层与层之间是递推的关系

                                                         \frac{\partial J}{\partial z^{l-1}}=\frac{\partial J}{\partial z^{l}}\frac{\partial z^{l}}{\partial z^{l-1}}=(W^{l})^T\frac{\partial J}{\partial z^{l}}\sigma^{'}(z^{l-1})

进而现在如果我们从最后一层递推到前面的层的话, \frac{\partial z^{l}}{\partial z^{l-1}}成为了需要关键计算的,对于普通的DNN层的话,\frac{\partial z^{l}}{\partial z^{l-1}}结果就是上式中去掉\frac{\partial J}{\partial z^{l}}的计算结果,下面我们讨论卷积层前后的z^l-1和z^l的关系。

我们依然以上面的例子为例,3*3的a^l-1输入,2*2卷积核,1步长,输出为2*2的z^l,我们把卷积前后的结果展开,左侧为卷积后的结果z^l,右侧为卷积前的结果a^l-1,我们先讨论,z^l和a^l-1的关系

                                          z_{11}=a_{11}w_{11}+a_{12}w_{12}+a_{21}w_{21}+a_{22}w_{22}\\

                                          z_{12}=a_{12}w_{11}+a_{13}w_{12}+a_{22}w_{21}+a_{23}w_{22}\\

                                          z_{11}=a_{21}w_{11}+a_{22}w_{12}+a_{31}w_{21}+a_{32}w_{22}\\

                                          z_{11}=a_{22}w_{11}+a_{23}w_{12}+a_{32}w_{21}+a_{33}w_{22}

根据之前的递推公式,我们也可以得出

                                                                                  \frac{\partial J}{\partial a^{l-1}} = \frac{\partial J}{\partial z^l}\frac{\partial z^l}{\partial a^{l-1}}

从上面的公式我们可以得出例子中每个\frac{\partial z^l}{\partial a^{l-1}}的计算结果。由于上一层的输入包含9个数据,a11与公式1有关,a12与公式1、公式2有关,a13与公式2有关,a21与公式1、公式3有关,a22与四个公式都有关,a23与公式2、公式4有关,a31与公式3有关,a32与公式3、公式4有关,a33与公式4有关。所以上一层a的梯度误差可能和多个输出相关。

                                                                                 \frac{\partial J }{\partial a_{11}}=\frac{\partial J }{\partial z_{11}}w_{11}

                                                                            \frac{\partial J }{\partial a_{12}}=\frac{\partial J }{\partial z_{11}}w_{12}+\frac{\partial J }{\partial z_{12}}w_{11} 

                                                                                \frac{\partial J }{\partial a_{13}}=\frac{\partial J }{\partial z_{12}}w_{12}

                                                                           \frac{\partial J }{\partial a_{21}}=\frac{\partial J }{\partial z_{11}}w_{21}+\frac{\partial J }{\partial z_{21}}w_{11}

                                                         \frac{\partial J }{\partial a_{22}}=\frac{\partial J }{\partial z_{11}}w_{22}+\frac{\partial J }{\partial z_{12}}w_{21}+\frac{\partial J }{\partial z_{21}}w_{12}+\frac{\partial J }{\partial z_{22}}w_{11}

                                                                           \frac{\partial J }{\partial a_{23}}=\frac{\partial J }{\partial z_{12}}w_{22}+\frac{\partial J }{\partial z_{22}}w_{12}

                                                                                \frac{\partial J }{\partial a_{31}}=\frac{\partial J }{\partial z_{21}}w_{21}

                                                                           \frac{\partial J }{\partial a_{32}}=\frac{\partial J }{\partial z_{21}}w_{22}+\frac{\partial J }{\partial z_{22}}w_{21}

                                                                                \frac{\partial J }{\partial a_{33}}=\frac{\partial J }{\partial z_{22}}w_{22}

上面的操作可以用一个卷积的形式来表示,为了符合梯度计算,我们在误差矩阵周围添加了一圈0。然后将卷积核翻转后(上下、左右)进行卷积操作,便算出来了上一层输入的误差

                                                   \begin{pmatrix} 0 & 0 & 0 & 0\\ 0 & \frac{\partial J}{\partial z_{11}} & \frac{\partial J}{\partial z_{12}} &0 \\ 0 & \frac{\partial J}{\partial z_{21}} & \frac{\partial J}{\partial z_{22}} &0 \\ 0 & 0 & 0 & 0 \end{pmatrix}*\begin{pmatrix} w_{22} & w{21}\\ w_{12} & w_{11} \end{pmatrix}=\begin{pmatrix} \frac{\partial J}{\partial a_{11}}& \frac{\partial J}{\partial a_{12}} & \frac{\partial J}{\partial a_{13}} \\ \frac{\partial J}{\partial a_{21}} & \frac{\partial J}{\partial a_{22}} & \frac{\partial J}{\partial a_{23}} \\ \frac{\partial J}{\partial a_{31}} & \frac{\partial J}{\partial a_{32}} & \frac{\partial J}{\partial a_{33}} \end{pmatrix} 

现在我们算出了卷积层之间过渡的递推公式,即卷积层后的输出的误差和旋转卷积核的卷积结果\frac{\partial J }{\partial a}\frac{\partial J }{\partial z}的计算,\frac{\partial J }{\partial z}=\frac{\partial J }{\partial a}\sigma^{'}(z))。所以我们现在已经求出了卷积层连续过渡的关键因素(等同于DNN中的\frac{\partial z^{l}}{\partial z^{l}}\frac{\partial z^{l}}{\partial z^{l-1}})。

PS:我们最后一层的\frac{\partial J}{\partial z^{l}}可以根据损失函数的最后的形式求出,然后前面层的结果,根据上面的递推结果可以求出。即下面的公式:

                                                                      \frac{\partial J}{\partial z^{l-1}}=\frac{\partial J}{\partial z^{l}}*rot180(W^l)\sigma^{'}(z^{l-1})

五、已知卷积层的\frac{\partial J}{\partial z^{l}},推导该层的W、b的梯度

现在我们已经求出了每一个卷积层的\frac{\partial J}{\partial z^{l}},现在我们推导该层的W、b的梯度如何求解。

注意到卷积层z和W、b的关系为:

                                                                    z^{l}=a^{l-1}*W^l+b^l

因此我们有:

                                                                 \frac{\partial J}{\partial W^l}=\frac{\partial J}{\partial z^l}\frac{\partial z^l}{\partial W^l}=a^{l-1}*\frac{\partial J}{\partial z^l} 

这里同样,我们以上一节中的例子说明,卷积层输入层的数据为3*3,卷积核大小为2*2。根据下面的公式,我们可以看出权值w和所有的输出都有关系,而我们的输出的误差\frac{\partial J}{\partial z^{l}}已经可以求出来

                                          z_{11}=a_{11}w_{11}+a_{12}w_{12}+a_{21}w_{21}+a_{22}w_{22}\\

                                          z_{12}=a_{12}w_{11}+a_{13}w_{12}+a_{22}w_{21}+a_{23}w_{22}\\

                                          z_{11}=a_{21}w_{11}+a_{22}w_{12}+a_{31}w_{21}+a_{32}w_{22}\\

                                          z_{11}=a_{22}w_{11}+a_{23}w_{12}+a_{32}w_{21}+a_{33}w_{22}

所以我们可以得出下面的 \frac{\partial J}{\partial w}:

                                        \frac{\partial J}{\partial w_{11}}=a_{11}\frac{\partial J}{\partial z_{11}}+a_{12}\frac{\partial J}{\partial z_{12}}+a_{21}\frac{\partial J}{\partial z_{21}}+a_{22}\frac{\partial J}{\partial z_{22}}\\

                                        \frac{\partial J}{\partial w_{12}}=a_{12}\frac{\partial J}{\partial z_{11}}+a_{13}\frac{\partial J}{\partial z_{12}}+a_{22}\frac{\partial J}{\partial z_{21}}+a_{23}\frac{\partial J}{\partial z_{22}}\\

                                        \frac{\partial J}{\partial w_{21}}=a_{21}\frac{\partial J}{\partial z_{11}}+a_{22}\frac{\partial J}{\partial z_{12}}+a_{32}\frac{\partial J}{\partial z_{21}}+a_{33}\frac{\partial J}{\partial z_{22}}\\

                                         \frac{\partial J}{\partial w_{22}}=a_{22}\frac{\partial J}{\partial z_{11}}+a_{23}\frac{\partial J}{\partial z_{12}}+a_{32}\frac{\partial J}{\partial z_{21}}+a_{33}\frac{\partial J}{\partial z_{22}}\\

最后我们可以得到四个式子,整理成矩阵的形式,可以表示成:

                                                       \frac{\partial J}{\partial w^l}=\begin{pmatrix} a_{11} & a_{12} & a_{13}\\ a_{21} & a_{22} & a_{23}\\ a_{31} &a_{32} & a_{33} \end{pmatrix}*\begin{pmatrix} \frac{\partial J}{\partial z_{11}}&\frac{\partial J}{\partial z_{12}} \\ \frac{\partial J}{\partial z_{21}} &\frac{\partial J}{\partial z_{22}} \end{pmatrix}

我们得出了,求解一个卷积层的W的梯度的结果,将这一层的输入数据和输出的结果偏差进行卷积,这是一个卷积核的计算方法,其余卷积核和这个方法一样。计算公式:

                                                                       \frac{\partial J}{\partial w^l}=a^{l-1}*\frac{\partial J}{\partial z^l}

关于b的梯度的计算,和DNN的稍微有点区别,因为所有卷积核的 \frac{\partial J}{\partial z^{l}}是一个三维张量,而b是一个向量,一般的做法是将每一个卷积核的误差项进行求和,得到一个误差向量。

                                                                    \frac{\partial J}{\partial b^l}=\sum_{u,v}(\frac{\partial J}{\partial z^l})_{u,v}

六,总结

 至此我们推导完了CNN的卷积层和池化层的梯度计算方式,我们来进行总结一下。

1、首先,所有的梯度的推导计算过程,计算出该层的\frac{\partial J}{\partial z^{l}}最重要(神经网络的层数从第一个隐藏层开始算起),然后该层的W,b的梯度,可以根据z、w、b的关系式求出。

2、其次层与层之间的递推过渡过程为第二个重点,也就是从\frac{\partial J}{\partial z^{l}}推导上一层的\frac{\partial J}{\partial z^{l-1}},针对DNN、池化、卷积层我们分别讨论了各自的过渡过程。

DNN:\frac{\partial J}{\partial z^{l-1}}=\frac{\partial J}{\partial z^{l}}\frac{\partial z^{l}}{\partial z^{l-1}}=(W^{l})^T\frac{\partial J}{\partial z^{l}}\sigma^{'}(z^{l-1})

池化层:\frac{\partial J}{\partial z^{l-1}}=upsample(\frac{\partial J}{\partial z^{l}}).\sigma^{'}(z^{l-1})    ,池化层需要做一个上采样的过程

卷积层:\frac{\partial J}{\partial z^{l-1}}=\frac{\partial J}{\partial z^{l}}*rot180(W^l)\sigma^{'}(z^{l-1}) ,卷积层输出的误差和旋转卷积核的卷积,然后和激活函数的导相乘,和DNN唯一的区别就是W。

3、最后我们求出了每一层的\frac{\partial J}{\partial z^{l}},然后就是求W和b的导数的过程。DNN可以直接根据z、w、b的相乘公式求解出来;池化层没有参数,所以不必要求解;CNN的卷积层包含参数需要求解。

DNN:  \frac{\partial J}{\partial W^l}=\frac{\partial J}{\partial z^l}(a^{l-1})^T                       \frac{\partial J}{\partial b^l}=\frac{\partial J}{\partial z^l}

卷积层:\frac{\partial J}{\partial w^l}=a^{l-1}*\frac{\partial J}{\partial z^l}                       \frac{\partial J}{\partial b^l}=\sum_{u,v}(\frac{\partial J}{\partial z^l})_{u,v}

  • 25
    点赞
  • 103
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
卷积神经网络(Convolutional Neural Network,CNN)是一种常用于图像处理和计算机视觉任务的深度学习模型。卷积层CNN中的核心组件之一,它通过卷积操作提取输入数据的特征。 在卷积层反向传播推导中,我们需要计算损失函数对于卷积层输入、权重和偏置的梯度。下面是卷积层反向传播推导的步骤: 1. 计算损失函数对于卷积层输出的梯度: 首先,根据损失函数的定义,计算损失函数对于卷积层输出的梯度。这个梯度可以通过使用链式法则从后一层传播过来的梯度计算得到。 2. 计算损失函数对于卷积层权重的梯度: 使用卷积操作的性质,将损失函数对于卷积层输出的梯度与输入数据进行卷积操作,得到损失函数对于卷积层权重的梯度。 3. 计算损失函数对于卷积层输入的梯度: 使用卷积操作的性质,将损失函数对于卷积层输出的梯度与卷积层权重进行卷积操作,得到损失函数对于卷积层输入的梯度。 4. 计算损失函数对于卷积层偏置的梯度: 将损失函数对于卷积层输出的梯度按照通道求和,得到每个通道的梯度,即损失函数对于卷积层偏置的梯度。 以上是卷积层反向传播推导的基本步骤。在实际应用中,还需要考虑批量处理、激活函数等因素。如果你对某个具体的CNN模型或者反向传播的细节有更具体的问题,可以告诉我。
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值