理解back propagation反向传播

作用

首先需要明白back propagation的作用:
深度学习的训练是成本函数(cost function)最小化的过程,一般采取梯度下降法求解。那么怎么计算梯度呢?这就要用到back propagation了。
计算一个数学表达式的梯度是很直接的,但计算是昂贵的。而反向传播算法使用简单的方法有效的减少了计算量。

误解

反向传播经常被误解为神经网络的整个学习算法。 实际上,反向传播仅用于计算梯度,然后另一种算法(如随机梯度下降SGD)利用反向传播得到的梯度进行学习。

链式法则

下面以求 f(x,y,z)=(x+y)z 的偏导为例:
引入一个中间变量 q ,将公式分成两部分: q=x+y f=qz

理解back propagation反向传播_第1张图片

上图的真实值计算线路展示了计算的视觉化过程。前向传播从输入计算到输出(绿色),反向传播尾部开始,根据链式法则递归地向前计算梯度(显示为红色),一直到网络的输入端。可以认为,梯度是从计算链路中回流。


利用链式法则我们知道:

fx=fqqx

在实际操作中,这只是简单地将两个梯度数值相乘。反向传播尾部开始,根据链式法则递归地向前计算梯度。

以上图为例,反向传播从从最上层的节点f开始,初始值为1,以层为单位进行处理。节点q接受f发送的1并乘以该节点的偏导值-4等于-4,节点z接受f发送的1并乘以该节点的偏导值3等于3,至此第二层完毕,求出各节点总偏导值并继续向下一层发送。节点q向x发送-4并乘以偏导值1等于-4,节点q向y发送-4并乘以偏导值1等于-4,至此第三层完毕,节点x,y的偏导值都为-4,即顶点f对x,y的偏导数均为-4.

示例代码如下:

# 设置输入值
x = -2; y = 5; z = -4

# 进行前向传播
q = x + y # q becomes 3
f = q * z # f becomes -12

# 进行反向传播:
# 首先回传到 f = q * z
dfdz = q # df/dz = q, 所以关于z的梯度是3
dfdq = z # df/dq = z, 所以关于q的梯度是-4
# 现在回传到q = x + y
dfdx = 1.0 * dfdq # dq/dx = 1. 这里的乘法是因为链式法则
dfdy = 1.0 * dfdq # dq/dy = 1

用向量化操作计算梯度

矩阵相乘的梯度:可能最有技巧的操作是矩阵相乘(也适用于矩阵和向量,向量和向量相乘)的乘法操作:

# 前向传播
W = np.random.randn(5, 10)
X = np.random.randn(10, 3)
D = W.dot(X)

# 假设我们得到了D的梯度
dD = np.random.randn(*D.shape) # 和D一样的尺寸
dW = dD.dot(X.T) #.T就是对矩阵进行转置
dX = W.T.dot(dD)

提示:要分析维度!注意不需要去记忆dW和dX的表达,因为它们很容易通过维度推导出来。例如,权重的梯度dW的尺寸肯定和权重矩阵W的尺寸是一样的,而这又是由X和dD的矩阵乘法决定的(在上面的例子中X和W都是数字不是矩阵)。总有一个方式是能够让维度之间能够对的上的。例如,X的尺寸是[10x3],dD的尺寸是[5x3],如果你想要dW和W的尺寸是[5x10],那就要dD.dot(X.T)。

参考

  1. cs231n 课程笔记翻译:反向传播笔记
  2. deep learning book 6.5节
  3. https://www.zhihu.com/question/27239198

你可能感兴趣的:(机器学习)