Keras自定义丢失实现:ValueError:一个操作对gradien没有'None'

2024-09-28 05:20:23 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在尝试实现这个loss函数:MCFD_loss_function 来自此文档(P6):Loss functions

所以我创建了一个新函数如下:

def mcfd_loss(y_true, y_pred):
    return K.sum( # ∑
        K.cast(
            K.greater( # only values greater than 0 (+ float32 cast)
                  K.dot(K.sign(y_pred),  # π
                        K.sign(y_true))
           , 0)
        , 'float32')
    )

但是,当我开始训练时,会出现以下错误:

ValueError: An operation has None for gradient. Please make sure that all of your ops have a gradient defined (i.e. are differentiable). Common ops without gradient: K.argmax, K.round, K.eval.

我不知道我漏掉了哪一点。这个错误似乎是由于我使用了更大的函数而引起的。我不知道这个错误是什么意思,也不知道如何纠正我的问题。

谢谢。


Tags: 函数文档true错误functionopsgreatersign
1条回答
网友
1楼 · 发布于 2024-09-28 05:20:23

您希望loss函数检查sign(f_(t,1))*sign(Y_(t+1))是否大于0。由于sign在0处不可微,我建议使用softsign

由于greate-than函数也不可微,因此可以使用以下近似值(参见here):maxϵ(x,y):= 0.5(x + y + absϵ(x − y)),其中absϵ(x):=sqrt(x^2 + ϵ)ϵ > 0。为了简单起见,我将在下面的代码示例中将此近似值称为greater_approx。(注意,您只需插入上面的计算)

查看loss函数的定义,您必须将总和除以预测数(K.get_variable_shape(y_pred)[0])(还要加一个减号)。P对应于根据Loss Functions in Time Series Forecasting paper的预测数。

总之,你的损失函数应该是这样的:

def mcfd_loss(y_true, y_pred):
   return - (1/K.get_variable_shape(y_pred)[0]) * K.sum( # ∑
      K.cast(
         greater_approx( # only values greater than 0 (+ float32 cast)
            K.dot(K.softsign(y_pred),  # π
                    K.softsign(y_true))
         , 0)
      , 'float32')
   )

最后一句话:对于在Keras中使用自定义丢失函数,请签出此SO question

相关问题 更多 >

    热门问题