【问题标题】:Tensor math with tensorflow backend带有 tensorflow 后端的张量数学
【发布时间】:2018-02-02 19:37:45
【问题描述】:

我在使用 keras 训练我的 LSTM 时尝试添加自定义指标。见以下代码:

from keras.models import Sequential
from keras.layers import Dense, LSTM, Masking, Dropout
from keras.optimizers import SGD, Adam, RMSprop
import keras.backend as K
import numpy as np

_Xtrain = np.random.rand(1000,21,47)
_ytrain = np.random.randint(2, size=1000)

_Xtest = np.random.rand(200,21,47)
_ytest = np.random.randint(1, size=200)

def t1(y_pred, y_true):
    return K.tf.count_nonzero((1 - y_true))

def t2(y_pred, y_true):
   return K.tf.count_nonzero(y_true)

def build_model():
    model = Sequential()
    model.add(Masking(mask_value=0, input_shape=(21, _Xtrain[0].shape[1])))
    model.add(LSTM(32, return_sequences=True))
    model.add(LSTM(64, return_sequences=False))
    model.add(Dense(1, activation='sigmoid'))
    rms = RMSprop(lr=.001, decay=.001)
    model.compile(loss='binary_crossentropy', optimizer=rms, metrics=[t1, t2])
    return model

model = build_model()

hist = model.fit(_Xtrain, _ytrain, epochs=1, batch_size=5, validation_data=(_Xtest, _ytest), shuffle=True)

以上代码的输出如下:

训练 1000 个样本,验证 200 个样本 纪元 1/1 1000/1000 [===============================] - 5s - 损失:0.6958 - t1: 5.0000 - t2: 5.0000 - val_loss:0.6975 - val_t1:5.0000 - val_t2:5.0000

因此,t1 和 t2 两种方法似乎都产生了完全相同的输出,这让我感到困惑。可能出了什么问题,我怎样才能得到 y_true 的互补张量?

背景故事:我试图为我的模型编写自定义指标(F1 分数)。 Keras 似乎没有那些现成的。如果有人知道更好的方法,请帮助我指出正确的方向。

【问题讨论】:

    标签: python tensorflow keras


    【解决方案1】:

    处理此问题的一种简单方法是改用回调。按照 issue 的逻辑,您可以指定一个指标回调,使用 sci-kit learn 计算任何指标。例如,如果要计算 f1,可以执行以下操作:

    from keras.models import Sequential
    from keras.layers import Dense, LSTM, Masking, Dropout
    from keras.optimizers import SGD, Adam, RMSprop
    import keras.backend as K
    from keras.callbacks import Callback
    import numpy as np
    
    from sklearn.metrics import f1_score
    
    _Xtrain = np.random.rand(1000,21,47)
    _ytrain = np.random.randint(2, size=1000)
    
    _Xtest = np.random.rand(200,21,47)
    _ytest = np.random.randint(2, size=200)
    
    class MetricsCallback(Callback):
        def __init__(self, train_data, validation_data):
            super().__init__()
            self.validation_data = validation_data
            self.train_data = train_data
            self.f1_scores = []
            self.cutoff = .5
    
        def on_epoch_end(self, epoch, logs={}):
            X_val = self.validation_data[0]
            y_val = self.validation_data[1]
    
            preds = self.model.predict(X_val)
    
            f1 = f1_score(y_val, (preds > self.cutoff).astype(int))
            self.f1_scores.append(f1)
    
    
    def build_model():
        model = Sequential()
        model.add(Masking(mask_value=0, input_shape=(21, _Xtrain[0].shape[1])))
        model.add(LSTM(32, return_sequences=True))
        model.add(LSTM(64, return_sequences=False))
        model.add(Dense(1, activation='sigmoid'))
        rms = RMSprop(lr=.001, decay=.001)
        model.compile(loss='binary_crossentropy', optimizer=rms, metrics=['acc'])
        return model
    
    model = build_model()
    
    hist = model.fit(_Xtrain, _ytrain, epochs=2, batch_size=5, validation_data=(_Xtest, _ytest), shuffle=True,
                    callbacks=[MetricsCallback((_Xtrain, _ytrain), (_Xtest, _ytest))])
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-04-21
      • 2019-04-10
      • 2020-04-29
      • 1970-01-01
      • 2023-03-07
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多