def _backward_cpu(self, context, dy): if isinstance(self.attrs._x, Node): N = len(dy) col = np.zeros((N, self.attrs._in_shape[0], self.attrs._kernel[0], self.attrs._kernel[1], self.attrs._out_shape[1], self.attrs._out_shape[2])) col_k = np.rollaxis(col.reshape( N, self.attrs._in_shape[0], -1, self.attrs._out_shape[1], self.attrs._out_shape[2]), 2) col_k[:] = dy / float(len(col_k)) dx = col2im(col, self.attrs._in_shape[1:], self.attrs._stride, self.attrs._padding) self.attrs._x._update_diff(context, dx)
def _backward_cpu(self, context, dy): if isinstance(self.attrs._x, Node): N = len(dy) index = self.attrs._index col = np.zeros((N, self.attrs._in_shape[0], self.attrs._kernel[0], self.attrs._kernel[1], self.attrs._out_shape[1], self.attrs._out_shape[2])) col_k = np.rollaxis(col.reshape( N, self.attrs._in_shape[0], -1, self.attrs._out_shape[1], self.attrs._out_shape[2]), 2) for i in np.ndindex(N, self.attrs._in_shape[0], self.attrs._out_shape[1], self.attrs._out_shape[2]): col_k[index[i]][i] = dy[i] dx = col2im(col, self.attrs._in_shape[1:], self.attrs._stride, self.attrs._padding) self.attrs._x._update_diff(context, dx)
def _oper_cpu(cls, x, w, b, in_shape, out_shape, kernel, stride, padding): z = np.tensordot(w, x, (0, 1)) z = np.rollaxis(z, 3) z = col2im(z, out_shape[1:], stride, padding) + b ret = cls._create_node(z) ret.attrs._x = x ret.attrs._w = w ret.attrs._b = b ret.attrs._in_shape = in_shape ret.attrs._kernel = kernel ret.attrs._stride = stride ret.attrs._padding = padding return ret
def _backward_cpu(self, context, dy): dy = to_value(dy) if isinstance(self.attrs._x, Node): dx = np.tensordot(self.attrs._w, dy, (0, 1)) dx = np.rollaxis(dx, 3) dx = col2im(dx, self.attrs._in_shape[1:], self.attrs._stride, self.attrs._padding) self.attrs._x._update_diff(context, dx) if isinstance(self.attrs._w, Node): self.attrs._w._update_diff(context, np.tensordot( dy, self.attrs._col, ([0, 2, 3], [0, 4, 5]))) if isinstance(self.attrs._b, Node): self.attrs._b._update_diff(context, np.sum(dy, (0, 2, 3), keepdims=True))
def _backward_cpu(self, context, dy, **kwargs): dy = to_value(dy) N, in_channels, in_h, in_w = self.attrs._x.shape groups = self.attrs._groups oCg = self.attrs._oCg iCg = self.attrs._iCg out_h, out_w = self.attrs._out_shape[-2:] k_h, k_w = self.attrs._kernel if isinstance(self.attrs._x, Node): dy_temp = dy.transpose(1, 0, 2, 3) dy_temp = dy_temp.reshape(groups, oCg, N * out_h * out_w) w_temp = self.attrs._w.reshape(groups, oCg, iCg * k_h * k_w) w_temp = w_temp.transpose(0, 2, 1) dx = np.matmul(w_temp, dy_temp) dx = dx.reshape(groups * iCg, k_h, k_w, N, out_h, out_w) dx = np.rollaxis(dx, 3) dx = col2im(dx, self.attrs._in_shape[1:], self.attrs._stride, self.attrs._padding, self.attrs._dilation) self.attrs._x._update_diff(context, dx, **kwargs) if isinstance(self.attrs._w, Node): col_temp = self.attrs._col col_temp = col_temp.transpose(0, 2, 1) dy_temp = dy.transpose(1, 0, 2, 3) dy_temp = dy_temp.reshape(groups, oCg, N * out_h * out_w) dw = np.matmul(dy_temp, col_temp) dw = dw.reshape(groups * oCg, iCg, k_h, k_w) self.attrs._w._update_diff(context, dw, **kwargs) if isinstance(self.attrs._b, Node): self.attrs._b._update_diff(context, np.sum(dy, (0, 2, 3), keepdims=True), **kwargs)