mxnet中自定义损失函数,并自动求导

mxnet中如果想自定义一个损失函数,并且利用autograd模块求导,需要重写该损失函数的前向和后向函数,下面以mxnet中一个例子来说明

class sigmoid(mx.autograd.Function):
    def forward(self, x):
        y = 1 / (1 + mx.nd.exp(-x))
        self.save_for_backward(y)
        return y

    def backward(self, dy):
        # backward takes as many inputs as forward's return value,
        # and returns as many NDArrays as forward's arguments.
        y, = self.saved_tensors
        return dy * y * (1-y)

 

以上是一个sigmoid函数的实例,首先计算出前向表达式 y = 1 / (1 + mx.nd.exp(-x)),由于反向传播需要用到,保存为self.saved_tensors,反向传播时,dy为正向传播时输出的导数,返回一个同正向传播输入具有相同shape的值。

func = sigmoid()
x = mx.nd.random.uniform(shape=(10,))
x.attach_grad()

with mx.autograd.record():
    m = func(x)
    m.backward()

-------------------------------分割线-----------------------------------------------

说一说用这种方式自定义loss的一个坑,由于训练过程中每次迭代都要新建一个Function的实例,而Function中又保存了saved_tensors等中间张量,计算的异步特性导致重新申请新的显存的速度超过显存回收的速度,因此训练时显存一直往上涨!最后的解决方案,每次迭代后手动释放自定义loss中saved_tensors等中间张量,并添加同步nd.waitall()

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值