非线性损耗组合

时间:2019-06-19 13:35:38

标签: tensorflow keras

我的网络有2个输出。我试图在两个项上造成损失,这不是两个损失的线性和:

def weightedBCE(y_true, y_pred):
    assert y_pred.shape[2] == 2
    y_pred_val = y_pred[:,:,0]
    stds = y_pred[:,:,1]
    bce = K.binary_crossentropy(y_true, y_pred_val)
    loss = bce * (1. + LAM*stds )
    return loss

我模型的最后一层是这样定义的(outSall具有3个值):

std = make_std_model()(outSall)
final = Dense(1, activation="sigmoid")(outSall)

output = concatenate([DSAfinal, std ], axis=-1)

但是它不起作用,因为Kears希望每个输出具有1个损失函数。我的损失使网络的两个输出一起使用。

第一个输出是具有二进制交叉熵损失的标准分类,但我希望将其乘以(1+ LAM* stds),并用一个λ因子乘以stdsstds是网络的第二个输出。

我该怎么做?

  

声明y_pred.shape [2] == 2

     

IndexError:列表索引超出范围

更新: 我有一个额外的索引,现在已修复。见下文。但是我在下面粘贴了一个错误。

def weightedBCE(y_true, y_pred):
    assert y_pred.shape[1] == 2
    y_pred_val = y_pred[:,0]
    stds = y_pred[:,1]
    bce = K.binary_crossentropy(y_true, y_pred_val)
    loss = bce * (1. + LAM*stds )
    return loss
  

ValueError:登录件和标签的形状必须相同((?,)vs(?,?)

Update2:

Keras假定y_true与y_pred具有相同的形状。这是问题所在。将损失更改为:

def weightedBCE(y_true, y_pred):
    assert y_pred.shape[1] == 2
    y_pred_val = y_pred[:,0]
    stds = y_pred[:,1]
    bce = K.binary_crossentropy(y_true[:,0], y_pred_val)
    loss = bce * (1. + LAM*stds )
    return loss

处理两个输出仍然存在一些问题,请参见Binary Cross Entropy not giving similar results when I have 2 outputs

1 个答案:

答案 0 :(得分:0)

不是创建具有两个输出的Keras模型,而是创建具有单个输出的Keras模型,该输出是两个张量的串联(您可以使用keras.layers.Concatenate)。然后,您可以像上面编写的那样使用单个自定义损失函数编译模型。