Hi,
I’m reading this tutorial
When I run this without any modification, this works well.
But when I call backward
on the output, my code crashes.
Fully running example is as follows.
import numpy as np
import mxnet as mx
from mxnet import gluon, autograd, nd
import os
class Dense(mx.operator.CustomOp):
def __init__(self, bias):
self._bias = bias
def forward(self, is_train, req, in_data, out_data, aux):
x = in_data[0].asnumpy()
weight = in_data[1].asnumpy()
y = x.dot(weight.T) + self._bias
self.assign(out_data[0], req[0], mx.nd.array(y))
def backward(self, req, out_grad, in_data, out_data, in_grad, aux):
print('sldjfsldjf')
x = in_data[0].asnumpy()
dy = out_grad[0].asnumpy()
dx = dy.T.dot(x)
self.assign(in_grad[0], req[0], mx.nd.array(dx))
@mx.operator.register("dense") #
class DenseProp(mx.operator.CustomOpProp):
def __init__(self, bias):
super(DenseProp, self).__init__(True)
# we use constant bias here to illustrate how to pass arguments
# to operators. All arguments are in string format so you need
# to convert them back to the type you want.
self._bias = float(bias)
def list_arguments(self):
return ['data', 'weight']
def list_outputs(self):
# this can be omitted if you only have 1 output.
return ['output']
def infer_shape(self, in_shapes):
data_shape = in_shapes[0]
weight_shape = in_shapes[1]
output_shape = (data_shape[0], weight_shape[0])
# return 3 lists representing inputs shapes, outputs shapes, and aux data shapes.
return (data_shape, weight_shape), (output_shape,), ()
def create_operator(self, ctx, in_shapes, in_dtypes):
# create and return the CustomOp class.
return Dense(self._bias)
class DenseBlock(mx.gluon.Block):
def __init__(self, in_channels, channels, bias, **kwargs):
super(DenseBlock, self).__init__(**kwargs)
self._bias = bias
self.weight = self.params.get('weight', shape=(channels, in_channels))
def forward(self, x):
ctx = x.context
return mx.nd.Custom(x, self.weight.data(ctx), bias=self._bias, op_type='dense')
dense = DenseBlock(3, 5, 0.1)
dense.initialize()
x = mx.nd.uniform(shape=(4, 3))
#x.attach_grad() # I tried this, but this was useless.
if autograd.record():
y = dense(x)
y.backward() # crashes.
print(x.grad)
Thank you for advance.