对误差反向传播的理解和学习

    关于反向传播,我非常推荐下面的一个在线书籍,其给出了非常详实、生动且易于理解的反向传播算法以及相关公式的推导,公式不繁杂是一大特点,Neural Networks and Deep Learning。本文将对其讲解给以归纳和总结,其中有些个人的见解,通篇将使用下图所示神经网络。

一、符号假设

损失函数为 C

第 l 层的第 j 个神经元表示为 nr_j^l

l 层的第 j 个神经元的偏置为 b_j^l,输入层无偏置

l-1 层的第 k 个神经元与第 l 层的第 j 个神经元之间的的权重为 w^l_{jk}l\geqslant 1

l 层的第 j 个神经元的激活值为 a_j^l

l 层的第 j 个神经元的输入值为 z_j^l=\sum_{k=1}^{n_{l-1}}w_{jk}^l+b_j^l,其中 n_{l-1} 表示第 l-1 层的神经元数量

二、什么是误差

    BP算法的全称是误差反向传播算法 ,本节来说下什么是误差,并结合下图来理解误差。

    现在,如果 nr_1^1 的输入发生变化,C 的变化为

                                                                                         \frac{\partial C}{\partial z_1^1}\Delta z_1^1

    假设 \Delta z_1^1 的变化较小。如果偏导项较大,且与 \Delta z_1^1 的符号相反,损失就会降低;反之,如果偏导项接近于零,那么无论 \Delta z_1^1 变化多大,损失的变动都不会很明显。那么,我们可以认为 C 的变化量由 \frac{\partial C}{\partial z_1^1} 来决定。\frac{\partial C}{\partial z_1^1} 越大,C 下降的空间就越大;反之,C 下降的空间就越小。因此,\frac{\partial C}{\partial z_1^1}  便可以用来度量学习误差。

 

三、单样本误差计算

    本节假定神经网络的输入仅有一个样本,后面会对多个样本下的误差计算进行推导。用 \delta _j^l 表示 nr_j^l 的误差。稍后会发现,对误差的计算将关系到对权重和偏置的偏导计算。假定损失函数为均方误差,那么输出层的误差为:

                                                              \delta^L=\begin{bmatrix} \delta _1^L\\ \delta _2^L\\ .\\ .\\ .\\ \delta _{n_L}^L \end{bmatrix} =\begin{bmatrix} \frac{\partial C}{\partial Z_1^L}\\ \frac{\partial C}{\partial Z_2^L}\\ .\\ .\\ .\\ \frac{\partial C}{\partial Z_{n_L}^L} \end{bmatrix} = \begin{bmatrix} \frac{\partial C}{\partial A_1^L}\frac{\partial A_1^L}{\partial Z_1^L}\\ \frac{\partial C}{\partial A_2^L}\frac{\partial A_2^L}{\partial Z_2^L}\\ .\\ .\\ .\\ \frac{\partial C}{\partial A_{n_L}^L}\frac{\partial A_{n_L}^L}{\partial Z_{n_L}^L} \end{bmatrix} = \begin{bmatrix} \textbf{\textit{a}}^L_1-\textbf{y}_1\\ \textbf{\textit{a}}^L_2-\textbf{y}_2\\ .\\ .\\ .\\ \textbf{\textit{a}}^L_{N_L}-\textbf{y}_{n_L} \end{bmatrix} \odot \begin{bmatrix} \sigma'(\textbf{\textit{z}}^L_1)\\ \sigma'(\textbf{\textit{z}}^L_2)\\ .\\ .\\ .\\ \sigma'(\textbf{\textit{z}}^L_{n_L}) \end{bmatrix}

    其中,\textbf{\textit{a}}^L 是输出层的激活向量, \textbf{y}是样本标签向量。单个神经元的误差为:

                                                                                             \delta _j^L=\frac{\partial C}{\partial z_j^L}=\frac{\partial C}{\partial a_j^L}\cdot \frac{\partial a_j^L}{\partial z_j^L}=\frac{\partial C}{\partial a_j^L} \sigma ^{'}\left ( z_j^L \right )

    误差反向传播体现在相邻层的误差存在依赖:

                                                                 \large \delta ^l= \begin{bmatrix} \sum_{i=1}^{n_{l+1}}\frac{\partial C}{\partial Z^{l+1}_i}\frac{\partial Z^{l+1}_i}{\partial A_1^l}\frac{\partial A^l_1}{\partial Z_1^l}\\ \sum_{i=1}^{n_{l+1}}\frac{\partial C}{\partial Z^{l+1}_i}\frac{\partial Z^{l+1}_i}{\partial A_2^l}\frac{\partial A^l_2}{\partial Z_2^l}\\ .\\ .\\ .\\ \sum_{i=1}^{n_{l+1}}\frac{\partial C}{\partial Z^{l+1}_i}\frac{\partial Z^{l+1}_i}{\partial A_{n_l}^l}\frac{\partial A^l_{n_l}}{\partial Z_{n_l}^l} \end{bmatrix} =((\textbf{\textit{w}}^{l+1})^T\delta ^{l+1}) \ \bigodot \ \sigma^{'} (\textbf{\textit{z}}^l)

    为了更加直观的理解上式,不妨来看一下其非向量表达形式

                                                                                                 \delta_j ^l=(\delta ^{l+1}\sum_{k=1}^{N_{l+1}}\textbf{\textit{w}}_{jk}^{l+1})\ast \ \sigma^{'}(\textbf{\textit{z}}_j^l)

      第一项是第 l+1 层各个神经元的学习误差的加权,第二项是激活函数对 \textbf{\textit{z}}_j^l 的偏导,表示激活值的变化率。其表达的直观意义是什么那? 结合下图和自己的理解来浅谈一下。

      聚焦 nr_1^1,第二层每个神经元的误差和第一层每个神经元是存在关系的,如nr_1^2 的误差的 20% 由 nr_1^1 导致,50% 由 nr_2^1 所致, 30% 由 nr_3^1 所致,而这些值恰是连接 nr_1^2 的权重值。那么在反向计算误差时,很自然的第二层每个神经元会将对应的误差值成比例的推向前一层现在 nr_1^1 接收了第 二层各个神经元推过来的误差,同时误差被 \sigma^{'}(\textbf{\textit{z}}_j^l) 进行了制约。如果 \sigma^{'}(\textbf{\textit{z}}_j^l)  大于 1,误差会放大,学习能力被放大,反之,学习能力开始缩水,慢慢的会死掉。如何制约学习能力,也就是激活函数的选择,这是一个超参数的选择问题。

 

三、偏置和权重的导数

    通过链式求导能计算出 C 相对每个权重的导数

                                                                                             \frac{\partial C}{\partial w_{jk}^l}

    以及 C 相对每个偏置的导数

                                                                                               \frac{\partial C}{\partial b_{j}^l}

    但是,这样做的时间复杂度是相当高的,详见上文在线文档中的分析。实际上,通过借助误差的计算便可完成对权重和偏置的导数表达。关于偏置的导数,其表达如下

                                                                                          \frac{\partial C}{\partial b_{j}^l}=\delta _j^l

    很棒,我们得到 \delta _j^l 立马得到上式,链式推导如下

                                                                {\color{Blue} }\frac{\partial C}{\partial b_{j}^l}= \sum_{k}^{N_{l+1}}\frac{\partial C}{\partial a_k^{l+1}}\frac{\partial a_k^{l+1}}{\partial z_k^{l+1}}\frac{\partial z_k^{l+1}}{\partial a_j^{l}}\frac{\partial a_j^{l}}{\partial z_j^{l}}\frac{\partial z_j^l}{\partial b_j^l}  =\frac{\partial z_j^l}{\partial b_j^l}\frac{\partial C}{\partial z_j^{l}}=\frac{\partial C}{\partial z_j^{l}}=\delta _j^l

     权重的导数也有类似的表示如下

                                                                                      \frac{\partial C}{\partial w_{jk}^l} = a_k^{l-1}\delta _j^l

     链式推导如下

                                                                            \frac{\partial C}{\partial w_{jk}^l} = \frac{\partial C}{\partial a_j^l}\frac{\partial a_j^l}{\partial z_j^l}\frac{\partial z_j^l}{\partial w_{jk}^l}  = \frac{\partial C}{\partial a_j^l}\frac{\partial a_j^l}{\partial z_j^l}a_k^{l-1}  = \frac{\partial C}{\partial z_j^l}a_k^{l-1}

 

四、多样本误差计算

    前向和反向传播的计算一般是基于mini-batch进行的,在这种情况下,导数的计算可以充分利用矩阵计算上的效率优势。令 \delta_j^l (x_i) 表示 x_i 在 nr_j^l 上的误差,令 L(x_i) 表示 x_i 带来的损失,A^l_j(x_i) 表示 x_i 在 nr_j^l 上的激活输出。每个mini-batch里面含有 n 个样本,激活函数为Relu

    首先给出输出层误差 \delta ^L 的表示:

                                                                     \delta ^L=\begin{bmatrix} \delta _1^L\\ \delta _2^L\\ .\\ .\\ .\\ \delta _{n_L}^L \end{bmatrix} = \begin{bmatrix} \sum_{i=1}^{n}\delta _1^L(x_i)\\ \sum_{i=1}^{n}\delta _2^L(x_i)\\ .\\ .\\ .\\ \sum_{i=1}^{n}\delta _{n_L}^L(x_i)}) \end{bmatrix}

    任意中间层的误差 \delta ^l 表示为:

                                                                     \delta ^l=a=\begin{bmatrix} \delta _1^l\\ \delta _2^l\\ .\\ .\\ .\\ \delta _{n_l}^l \end{bmatrix} = \begin{bmatrix} \sum_{i=1}^{n}\begin{bmatrix} \delta ^{l+1}_1(x_i) & \delta ^{l+1}_2(x_i)& .& .& .& \delta^{l+1}_{n_{l+1}}(x_i) \end{bmatrix} \ast \begin{bmatrix} W_{11}^{l+1} & W_{21}}^{l+1}& .& .& .& W_{n_{l+1}1}}^{l+1} \end{bmatrix}^T\\ \sum_{i=1}^{n}\begin{bmatrix} \delta ^{l+1}_1(x_i) & \delta ^{l+1}_2(x_i)& .& .& .& \delta^{l+1}_{n_{l+1}}(x_i) \end{bmatrix} \ast \begin{bmatrix} W_{12}^{l+1} & W_{22}}^{l+1}& .& .& .& W_{n_{l+1}2}}^{l+1} \end{bmatrix}^T\\ .\\ .\\ .\\ \sum_{i=1}^{n}\begin{bmatrix} \delta ^{l+1}_1(x_i) & \delta ^{l+1}_2(x_i)& .& .& .& \delta^{l+1}_{n_{l+1}}(x_i) \end{bmatrix} \ast \begin{bmatrix} W_{1n_l}^{l+1} & W_{2n_l}}^{l+1}& .& .& .& W_{n_{l+1}n_l}}^{l+1} \end{bmatrix}^T \end{bmatrix}

    任意层权重的导数表示为:

                         \frac{\partial C}{\partial W^l}=\begin{bmatrix} \delta^{l}_1(x_1)& \delta^{l}_1(x_2)& .& .& .& \delta^{l}_1(x_n)\\ \delta^{l}_2(x_1)& \delta^{l}_2(x_2)& .& .& .& \delta^{l}_2(x_n)\\ .& & & & & .\\ .& .& & & & .\\ .& & .& & & .\\ \delta^{l}_{n_{l}}(x_1)& \delta^{l}_{n_{l}}(x_2)& .& .& .& \delta^{l}_{n_l}(x_n) \end{bmatrix} \ast \begin{bmatrix} A^{l-1}_1(x_1)& A^{l-1}_2(x_1)& .& .& .& A^{l-1}_{n_l}(x_1)\\ A^{l-1}_1(x_2)& A^{l-1}_2(x_2)& .& .& .& A^{l-1}_{n_l}(x_2)\\ .& & & & &. \\ .& & & & &. \\ .& & & & &. \\ A^{l-1}_1(x_n)& A^{l-1}_2(x_n)& .& .& .& A^{l-1}_{n_l}(x_n) \end{bmatrix}

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值