• 介绍
  • 简单表达式和解释梯度
  • 使用链式法则计算复合表达式
  • 反向传播直观理解
  • 模块化Sigmoid例子
  • 反向传播实践分段计算
  • 方向传播流的模式
  • 向量化梯度操作
  • 总结
  • 参考

介绍

这节介绍反向传播的直观理解。使用链式法则递归求导

函数 f(x) f(x),其中 x x是输入变量,我们需要计算xx的导数 ∇f(x) \nabla f(x)。这个函数 f(x) f(x)可以是loss函数,计算loss函数关于权重和偏置 W,b W,b的导数,依次更新它们。

简单表达式和解释梯度

函数有两个变量 f(x,y)=xy f(x,y)=xy,可以得到

f(x,y)=xy→∂f∂x=y∂f∂y=x

f(x,y) = x y \hspace{0.5in} \rightarrow \hspace{0.5in} \frac{\partial f}{\partial x} = y \hspace{0.5in} \frac{\partial f}{\partial y} = x

一个变量的导数,表示它的值变化时对整个表示式影响的大小。

∇f \nabla f表示偏导数向量, ∇f=[∂f∂x,∂f∂y]=[y,x] \nabla f = [\frac{\partial f}{\partial x}, \frac{\partial f}{\partial y}] = [y, x]

对加法求导:

f(x,y)=x+y→∂f∂x=1∂f∂y=1

f(x,y) = x + y \hspace{0.5in} \rightarrow \hspace{0.5in} \frac{\partial f}{\partial x} = 1 \hspace{0.5in} \frac{\partial f}{\partial y} = 1

对max算子求导

f(x,y)=max(x,y)→∂f∂x=1(x>=y)∂f∂y=1(y>=x)

f(x,y) = \max(x, y) \hspace{0.5in} \rightarrow \hspace{0.5in} \frac{\partial f}{\partial x} = \mathbb{1}(x >= y) \hspace{0.5in} \frac{\partial f}{\partial y} = \mathbb{1}(y >= x)
上面变量大的值才对表达式有影响,变量小的值,导数为零。

使用链式法则计算复合表达式

以一个稍微复杂一点的计算为例 f(x,y,z)=(x+y)z f(x,y,z) = (x + y)z,可以把这个函数分为2个 q=x+y q = x + y, f=qz f = qz。先对 q,z q,z求导得到 ∂f∂q=z,∂f∂z=q \frac{\partial f}{\partial q} = z, \frac{\partial f}{\partial z} = q,在用 q q对x,yx,y求导 ∂q∂x=1,∂q∂y=1 \frac{\partial q}{\partial x} = 1, \frac{\partial q}{\partial y} = 1,根据链式法则 ∂f∂x=∂f∂q∂q∂x \frac{\partial f}{\partial x} = \frac{\partial f}{\partial q} \frac{\partial q}{\partial x}

上面求解过程,可以用下图表示

上图中,绿色表示前向传播,红色表示反向传播。

反向传播直观理解

反向传播是局部处理过程。每个神经单元在得到输入后,可以立即计算两件事1、输出,2、关于输入的局部梯度。神经单元不需要知道整个网络的结构就可以完成这两件事。前向传播完成后,在反向传播时,只需要对路径上的局部梯度相乘就可以得到最终输出对于某个变量的梯度值。

模块化:Sigmoid例子

任何函数都可以看做一个神经元,可以把多个神经元组成一个,或把一个函数拆分为几个门单元。看下面的表达式

f(w,x)=11+e−(w0x0+w1x1+w2)

f(w,x) = \frac{1}{1+e^{-(w_0x_0 + w_1x_1 + w_2)}}
这个函数有多个计算组成,除了上面介绍的加、乘、max,还有四种:

f(x)=1x→dfdx=−1/x2fc(x)=c+x→dfdx=1f(x)=ex→dfdx=exfa(x)=ax→dfdx=a

f(x) = \frac{1}{x} \hspace{1in} \rightarrow \hspace{1in} \frac{df}{dx} = -1/x^2 \\\\ f_c(x) = c + x \hspace{1in} \rightarrow \hspace{1in} \frac{df}{dx} = 1 \\\\ f(x) = e^x \hspace{1in} \rightarrow \hspace{1in} \frac{df}{dx} = e^x \\\\ f_a(x) = ax \hspace{1in} \rightarrow \hspace{1in} \frac{df}{dx} = a
上面的计算过程可以用下图表示

其中 w=[2,−3,−3],x=[−1,−2] w = [2,-3,-3],x = [-1, -2]

sigmoid函数是常用的激活函数,对它的求导,计算如下

σ(x)=11+e−x→dσ(x)dx=e−x(1+e−x)2=(1+e−x−11+e−x)(11+e−x)=(1−σ(x))σ(x)

\sigma(x) = \frac{1}{1+e^{-x}} \\\\ \rightarrow \hspace{0.3in} \frac{d\sigma(x)}{dx} = \frac{e^{-x}}{(1+e^{-x})^2} = \left( \frac{1 + e^{-x} - 1}{1 + e^{-x}} \right) \left( \frac{1}{1+e^{-x}} \right) = \left( 1 - \sigma(x) \right) \sigma(x)

实现提示:分段反向传播。把前向传播分段进行,方便计算导数和反向传播。

反向传播实践:分段计算

有如下函数

f(x,y)=x+σ(y)σ(x)+(x+y)2

f(x,y) = \frac{x + \sigma(y)}{\sigma(x) + (x+y)^2}
先写代码实现forward

x = 3 # example values
y = -4# forward pass
sigy = 1.0 / (1 + math.exp(-y)) # sigmoid in numerator   #(1)
num = x + sigy # numerator                               #(2)
sigx = 1.0 / (1 + math.exp(-x)) # sigmoid in denominator #(3)
xpy = x + y                                              #(4)
xpysqr = xpy**2                                          #(5)
den = sigx + xpysqr # denominator                        #(6)
invden = 1.0 / den                                       #(7)
f = num * invden # done!                                 #(8)

在实现时,创建了一些中间变量sigy, num, sigx, xpy, xpysqr, den, invden,这些都是简单的表达式。在反向传播时,在这些变量前面加上d表示梯度

# backprop f = num * invden
dnum = invden # gradient on numerator                             #(8)
dinvden = num                                                     #(8)
# backprop invden = 1.0 / den
dden = (-1.0 / (den**2)) * dinvden                                #(7)
# backprop den = sigx + xpysqr
dsigx = (1) * dden                                                #(6)
dxpysqr = (1) * dden                                              #(6)
# backprop xpysqr = xpy**2
dxpy = (2 * xpy) * dxpysqr                                        #(5)
# backprop xpy = x + y
dx = (1) * dxpy                                                   #(4)
dy = (1) * dxpy                                                   #(4)
# backprop sigx = 1.0 / (1 + math.exp(-x))
dx += ((1 - sigx) * sigx) * dsigx # Notice += !! See notes below  #(3)
# backprop num = x + sigy
dx += (1) * dnum                                                  #(2)
dsigy = (1) * dnum                                                #(2)
# backprop sigy = 1.0 / (1 + math.exp(-y))
dy += ((1 - sigy) * sigy) * dsigy                                 #(1)
# done! phew

注意:
1、对前向传播过程中的变量进行缓存,因为在反向传播时也会用到。
2、如果 x,y x,y在前向传播时,使用了多次;那么在反向传播时要使用+=来代替=。我们要累积梯度,使用=会覆盖掉前面计算好的梯度。

方向传播流的模式

反向传播中的梯度可以直观的解释一下。神经网络中最常用的三个门单元为 add,mul,max add,mul,max,可以直观的看一下它们三个在反向传播中,对梯度的影响。

add:加法是把梯度不变的分到下一个门单元。
max:max算子是把梯度分到值比较大的一个单元。
mul:乘法是把梯度乘以一个值传到下一个门单元。 f=xy f=xy,那么传到 x x的梯度要乘以yy,同理 y y的梯度。

注意,权重和数据的乘积wTxiw^Tx_i,如果有某个权重很大,那么某个维度的输入数据梯度会很大,这样这个维度的数据对结果有很大影响。因此要正则化权重,限制梯度幅度。

向量化梯度操作

上面的例子都是单个变量的,神经网络中的运算都是以矩阵或向量为单位的。求梯度以及梯度反向传播,都可以用矩阵或向量乘法。

# forward pass
W = np.random.randn(5, 10)
X = np.random.randn(10, 3)
D = W.dot(X)# now suppose we had the gradient on D from above in the circuit
dD = np.random.randn(*D.shape) # same shape as D
dW = dD.dot(X.T) #.T gives the transpose of the matrix
dX = W.T.dot(dD)

注意,在分析梯度是,不用记住它的表达式,因为可以通过维度推导出来。dW维度和W维度大小一样,它等于dDX的乘积。

总结

1、对梯度有了直观理解,知道梯度如何在网络中传播,如何影响输出。
2、对梯度计算时,使用分段计算。把函数分为更小的模块,可以更好地计算梯度,使用链式法则得到最终梯度。

参考

Automatic differentiation in machine learning: a survey

cs231n-(4)反向传播相关推荐

  1. 【cs231n】反向传播笔记

    前言 首先声明,以下内容绝大部分转自知乎智能单元,他们将官方学习笔记进行了很专业的翻译,在此我会直接copy他们翻译的笔记,有些地方会用红字写自己的笔记,本文只是作为自己的学习笔记.本文内容官网链接: ...

  2. 机器学习笔记 - 使用python代码实现易于理解的反向传播

    一.反向传播概述 反向传播可以说是神经网络历史上最重要的算法--如果没有有效的反向传播,就不可能将深度学习网络训练到我们今天看到的深度.反向传播可以被认为是现代神经网络和深度学习的基石. 反向传播的最 ...

  3. 【CS231n】斯坦福大学李飞飞视觉识别课程笔记(十一):反向传播笔记

    [CS231n]斯坦福大学李飞飞视觉识别课程笔记 由官方授权的CS231n课程笔记翻译知乎专栏--智能单元,比较详细地翻译了课程笔记,我这里就是参考和总结. [CS231n]斯坦福大学李飞飞视觉识别课 ...

  4. # cs231n (四)反向传播

    cs231n (四)反向传播 标签(空格分隔): 神经网络 文章目录 cs231n (四)反向传播 0.回顾 1.引言 2. 通过简单表达式理解梯度 3. 链式法则计算复合函数 4. 如何理解反向传播 ...

  5. CS231n课程笔记翻译5:反向传播笔记

    译者注:本文智能单元首发,译自斯坦福CS231n课程笔记Backprop Note,课程教师Andrej Karpathy授权翻译.本篇教程由杜客翻译完成,堃堃和巩子嘉进行校对修改.译文含公式和代码, ...

  6. cs231n笔记5—反向传播/神经网络

    反向传播 神经网络 反向传播 问题陈述:这节的核心问题是,给定函数f(x),其中x是输入数据的向量,需要计算函数f关于x的梯度,也就是∇f(x). 反向传播是利用链式法则递归计算表达式的梯度的方法.理 ...

  7. 梯度反向传播(CS231n课程笔记翻译)

    CS231n课程笔记翻译:反向传播笔记 - 杜客的文章 - 知乎 译者注:本文智能单元首发,译自斯坦福CS231n课程笔记Backprop Note,课程教师Andrej Karpathy授权翻译.本 ...

  8. CS231n课程笔记翻译:反向传播笔记

    译者注:本文智能单元首发,译自斯坦福CS231n课程笔记Backprop Note,课程教师Andrej Karpathy授权翻译.本篇教程由杜客翻译完成,堃堃和巩子嘉进行校对修改.译文含公式和代码, ...

  9. CS231n 两层神经网络反向传播实现

    今天写了cs231n 作业1的两层神经网络的部分,听视频和看讲义的时候觉得挺简单的没在意,后来真正写的时候发现了问题,而且也领悟到了新的东西,反向传播代码实现的奥妙之处. 同时也把之前的loss函数梯 ...

  10. 【cs231n】Batchnorm及其反向传播

    文章目录 BatchNormalization 反向传播 其他Normalization方法 LayerNormalization InstanceNormalization GroupNormali ...

最新文章

  1. Centos安装tomcat,haproxy,jdk
  2. Material Design综合实例
  3. DZ论坛系统 UC_KEY拿webshell
  4. 怎么让电脑屏幕一直亮着_电脑屏幕总是闪烁?试试这个方法
  5. js des加密 java_Java实现与JS相同的Des加解密算法完整实例
  6. 之前安装vmware player卸载失败出现msi '' failed,就安装不vmware station
  7. Android M(6.0) 权限相关
  8. TCP之keepalive机制的应用场景
  9. [论文翻译]NEURAL MACHINE TRANSLATION BY JOINTLY LEARNING TO ALIGN AND TRANSLATE
  10. 如何批量从Excel文件中导入数据到数据库(二)
  11. php pdo查询sqlserver,php pdo sqlserver分页sql的处理
  12. 发现一个特给力的编写HTML/CSS的插件——Zen Coding
  13. 如何以16进制打开dll文件
  14. newifimini出厂固件_新路由newifi固件
  15. 整流六—PWM整流器无差拍控制 二(重复控制算法)
  16. 什么样的设计可以征服客户?
  17. 计算机的标准输入法,计算机操作系统标准教程 第4章 五笔字型输入法.pdf
  18. Word 2016 如何设置黑底白字
  19. 【VJudge】【Legilimens Contest 1】
  20. JS字符串截取 “指定字符” 前面和后面的内容!

热门文章

  1. 【学习笔记】Android基础知识回顾
  2. python人物关系可视化百年孤独_利用python对《乘风破浪的姐姐》可视化
  3. LQR控制器——简单实现与仿真
  4. Could not find a package configuration file provided by “std_msg“ with any of the following names:
  5. redis常见使用场景与实例
  6. 读书笔记(二十三):代码整洁
  7. 【⏰亲】今天冬至,早些回家!
  8. Android中收货地址管理Demo
  9. 【北大青鸟天府校区的Java专业怎么样?】
  10. DailyFi - 9.20|NFT 平台 Vera 将于明日在 Polkastarter 上 IDO