【问题标题】:Understanding neural network output >1 with sigmoid activation function使用 sigmoid 激活函数了解神经网络输出 >1
【发布时间】:2021-02-05 13:13:08
【问题描述】:

我正在尝试将卷积神经网络与线性模型相结合的模型。这是它的简化版本:

from tensorflow.keras import Sequential
from tensorflow.keras.experimental import WideDeepModel, LinearModel
num_classes = 1 ##(0='NO' or 1='YES')

cnn_model.Sequential()
cnn_model.add(Conv1D(20, 8, padding='same', activation='relu'))
cnn_model.add(GlobalAveragePooling1D())
cnn_model.add(Dropout(0.6))
cnn_model.add(Dense(num_classes, activation='sigmoid'))

linear_model = LinearModel()
combined_model = WideDeepModel(linear_model, cnn_model)
combined_model.compile(optimizer = ['sgd', 'adam'],
                            loss = ['mse','binary_crossentropy'], 
                         metrics = ['accuracy'])

性能非常好,一切似乎都很顺利,直到我按 pval 对预测进行排序,我可以看到预测 >1 即使我使用 sigmoid 激活,也就是我思想应该使一切都在 0 和 1 之间,并且没有线性模型的激活函数(但输入都按 0-1 缩放):

pred = [ 1 if a > threshold else 0 for a in combined_model.predict([dplus_test, X_test])]
pv = combined_model.predict([dplus_test, X_test])
pval = [a[0] for a in pv]
    true    pred    pval    dplus
1633    1   1   1.002850    15.22404
1326    1   1   1.001444    10.34983
1289    1   1   1.001368    10.03043
1371    1   1   1.000986    10.74037
1188    1   1   1.000707    8.902

我检查了数据的另一端,那些预测和我预期的一样,总是 >0。

    true    pred    pval    dplus
145     0   0   0.000463    1.81635
383     0   0   0.001023    3.24982
1053    0   0   0.001365    7.22535

到目前为止,这不是问题,没有崩溃,我对性能感到满意。

我想知道我对 sigmoid 激活函数的理解是否错误,或者组合模型中是否存在允许值超过 1 的东西,以及我是否可以相信这些结果。

【问题讨论】:

    标签: python tensorflow keras neural-network sigmoid


    【解决方案1】:

    这是因为您的 sigmoid 仅在 Deep 模型的输出上定义,WideDeepModel 组合两个模型的输出的方式是通过添加它们(并且您的 Wide 线性模型可以有任意输出)。由于您在损失中同时包含msebinary_crossentropy,因此组合模型实际上学会了输出接近预期范围的值。

    如果你只有binary_crossentropy,你可能会看到比1大得多的值,因为损失的公式是-p * log(q),其中q是你的网络的输出,你可以使损失任意小无限期地增加q,当您的输出有界时不会发生这种情况。

    WideDeepModel 有一个附加属性activation(参见docs),您可以在其中定义整个模型的激活函数。如果要在 0 和 1 之间压缩输出,请将其设置为 sigmoid

    combined_model = WideDeepModel(linear_model, cnn_model, activation='sigmoid')
    

    最后一点,根据我的经验,像这样结合均方误差和二元交叉熵并没有多大意义,实际上你会选择其中一个。

    【讨论】:

      猜你喜欢
      • 2014-01-06
      • 2017-01-14
      • 2018-05-16
      • 2020-10-09
      • 2019-08-02
      • 2014-01-18
      • 2017-12-08
      • 2014-03-26
      相关资源
      最近更新 更多