繁体   English   中英

Keras LSTM用于时间序列预测:预测特征向量

[英]Keras LSTM for timeseries prediction: predicting vectors of features

我有一个具有N个观测值和F个特征的时间序列数据集。 每个功能都可以显示(1),也可以不显示(0)。 因此,数据集将如下所示:

T    F1    F2    F3    F4    F5 ... F
0    1     0     0     1     0      0
1    0     1     0     0     1      1
2    0     0     0     1     1      0
3    1     1     1     1     0      0
...
N    1     1     0     1     0      0

我正在尝试使用基于LSTM的体系结构,根据观测值TW-T预测在时间T + 1出现哪些特征,其中W是某个时间窗口的宽度。 如果W = 4,则LSTM会“查看”过去的4个时间步长以进行预测。 LSTM期望3D输入,其形式为(number_batches,W,F)。 天真的Keras实现可能看起来像:

model = Sequential()
model.add(LSTM(128, stateful=True, batch_input_shape=(batch_size, W, F)))
model.add(Dense(F, activation='sigmoid'))

model.compile(loss='binary_crossentropy',
              optimizer='rmsprop',
              metrics=['accuracy'])
model.fit(x_train, y_train,
          batch_size=batch_size, epochs=250, shuffle=False,
          validation_data=(x_val, y_val))

我遇到的主要问题是:完整的数据集具有大量特征(> 200),并且很少能表现出特征,即0比1更为常见。神经网络只是学习设置所有值设置为0,从而实现高度的“准确性”。

本质上,我想对输入矩阵中的每个1加权以使其具有更高的重要性,但是我对如何在Keras中实现这一点感到困惑。 我知道sample_weight中有一个sample_weight选项,但是它如何工作? 例如,在我的示例中,我不知道如何实现它。 这是我所遇到问题的合理解决方案吗? 这类问题通常使用哪些优化器和损失函数?

这是我用于2D高度不平衡数据的损失函数,它工作得很好。 您可以将binary_crossentropy替换为另一种损失。

import keras.backend as K

def weightedByBatch(yTrue,yPred):

    nVec = K.ones_like(yTrue) #to sum the total number of elements in the tensor
    percent = K.sum(yTrue) / K.sum(nVec) #percent of ones relative to total
    percent2 = 1 - percent #percent of zeros relative to total   
    yTrue2 = 1 - yTrue #complement of yTrue (yTrue+ yTrue2 = full of ones)   

    weights = (yTrue2 * percent2) + (yTrue*percent)
    return K.mean(K.binary_crossentropy(yTrue,yPred)/weights)

对于您的3D数据,这可能有用,但也许您可以按列工作,为每个要素创建一对权重,而不是将所有要素加在一起。

可以这样进行:

def weightedByBatch2D(yTrue,yPred):

    nVec = K.ones_like(yTrue) #to sum the total number of elements in the tensor
    percent = K.sum(K.sum(yTrue,axis=0,keepdims=True),axis=1,keepdims=True) / K.sum(K.sum(nVec,axis=0,keepdims=True),axis=1,keepdims=True) #percent of ones relative to total
    percent2 = 1 - percent #percent of zeros relative to total   
    yTrue2 = 1 - yTrue #complement of yTrue (yTrue+ yTrue2 = full of ones)   

    weights = (yTrue2 * percent2) + (yTrue*percent)
    return K.mean(K.binary_crossentropy(yTrue,yPred)/weights)   

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM