【问题标题】:Neural network: Batch-version affine layer back-propagation weight matrix updation神经网络:批量版本仿射层反向传播权重矩阵更新
【发布时间】:2018-04-29 10:31:28
【问题描述】:

我正在尝试阅读一本关于深度学习的书,但我发现关于网络仿射层的部分内容令人困惑。假设我有一个接受一些手写数字(0 ~ 9)图像(mnist)的网络,它们被展平为一维数组,例如np.array([123, 255, 0, ...]) 它将输出每个可能输出的分数,例如np.array([0., 0., 0.3, 0., 0., 0.6, 0., 0., 0., 0.1])(所以图片可能是数字5)。

这是我的仿射层实现:

class AffineLayer(object):
    ...
    def backward(self, dy):
        dx = np.dot(dy, self._W.T)
        self._dW = np.dot(self._x.T, dy) # Question related part
        self._db = np.sum(dy, axis=0)
        dx = dx.reshape(self._original_x_shape)
        return dx
    ...

这里有一些解释:

  • self._W 是权重矩阵。
  • 这里关注的部分是self._dW = np.dot(self._x.T, y) # Question related part
  • 这条线来自一个等式:

    X * W + B = Y  
    (N,2) matrix product (2,3) (1,3) (N,3).

  • 符号(2,) 来自numpy.arrayX.shape 等。为了简化我的问题,我选择了这些维数。

术语结束,现在问题来了:

通过一些数学运算(省略),我们可以得出反向传播中使用的相等性,(因此代码中使用了self._dW = np.dot(self._x.T, y)):

d L T d L  
--- == X * ---  
d W d Y  
   
(2,3) (2,N) * (N,3).

请注意,无论我如何调整 N(即批量大小),dL/dW 的维度(L 权重矩阵的偏导数)都不会改变,并且始终是 @ 987654342@.

这是否意味着这些N 批次的总效果被合并/浓缩到dL/dW 中?这与我将如何实现输出层有关,例如softmax-cross-entropy 层作为最后一层。我目前对此的结论是N 批处理意味着进行反向传播N 次,并且需要将梯度dL/dW 除以N 来平均/摊销该批处理的总效果。但现在看来我只需要做一次,划分应该是“第一步”。

编辑:

我在最后一步也找到了似乎将它分开的版本mnielsen/neural-networks-and-deep-learning - GitHub,供参考。

由于 softmax-cross-entropy 层类是网络的最后一层,因此在反向传播中它将成为我上面提到的“第一步”:

class SoftmaxCrossEntropy(object):
    ...
    def backward(self, dout=1):
        batch_size = self._t.shape[0]
        # one-hot
        if self._t.size == self._y.size:
            dx = (self._y - self._t) / batch_size # <-- why divided by N here?
        else: # not one-hot
            dx = self._y * 1
            dx[np.arange(batch_size), self._t] -= 1
            dx = dx / batch_size       #    <-- why divided by N here?
        return dx
    ...

【问题讨论】:

    标签: python numpy neural-network


    【解决方案1】:

    是不是意味着将这N批输入的效果合并/浓缩到dW中?

    由于X 的第 i 行是与第 i 个展平图像相关的一维数组。如果我将X 转置为

      T  
      X , 然后是表示这些扁平图像的列。如果N增加,虽然

    结果的维度(dW)不会改变,计算每个元素的中间步骤

      T d L  
     dW = X * ---  
      d Y ,增加,表示

      N  
     dW = Sum ( pixel_info * class_scores_deriv. )  
      i,j n=1 i,n n,j , 其中N 是批次

    大小。明明每个class_scores_derivative_(n,j)“加入”dW_(i,j)的确定,但这意味着需要除以batch_size = N,因为上面的求和不是那个批次的平均效果,而是我需要的是dW到表示该批次的平均影响。如果我把class_scores_deriv.的每个元素分开,也就是一行
    dx = (self._y - self._t) / batch_size,那么

      N 1  
      Sum ( pixel_info * --- class_scores_deriv. )  
      n=1 i,n N n,j  
      1 N  
      = --- Sum ( pixel_info * class_scores_deriv. )  
      N n=1 i,n n,j  
      1  
      = --- dW  
      N , 这是我想要的真正的dW

    所以答案(我希望)应该是

    整批确定dW,但要浓缩它,需要SoftmaxCrossEntropy::backward(self, dout=1)中的划分。

    【讨论】:

      猜你喜欢
      • 2013-01-22
      • 1970-01-01
      • 1970-01-01
      • 2015-03-03
      • 2012-02-21
      • 2011-01-05
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多