设定固定的时间步长LSTM Keras模型的自由时间步长

时间:2018-11-30 22:56:26

标签: python tensorflow keras nlp lstm

我有一个执行两个任务的Keras LSTM多任务模型。一个是序列标记任务(因此我可以预测每个标记的标签)。另一个是使用堆叠在LSTM隐藏状态下的CNN在整个序列上进行全局分类的任务。

在我的设置中(不问原因),我只在培训期间需要CNN任务,但是它预测的标签在最终产品上没有用。因此,在Keras上,无需指定输入序列长度就可以训练LSTM模型。像这样:

l_input = Input(shape=(None,), dtype="int32", name=input_name)

但是,如果我添加了堆叠在LSTM隐藏状态下的CNN,则需要为模型设置固定的序列长度。

l_input = Input(shape=(timesteps_size,), dtype="int32", name=input_name)

问题是,一旦我以固定的时间step_size训练了模型,就无法再使用它来预测更长的序列。

在其他框架中,这不是问题。但是在Keras中,一旦训练了模型,我就无法摆脱CNN并更改其预期的输入形状。

这是模型的简化版本

l_input = Input(shape=(timesteps_size,), dtype="int32")
l_embs  = Embedding(len(input.keys()), 100)(l_input)
l_blstm = Bidirectional(GRU(300, return_sequences=True))(l_embs)

# Sequential output
l_out1  = TimeDistributed(Dense(len(labels.keys()),
                                activation="softmax"))(l_blstm)


# Global output
conv1  = Conv1D( filters=5 , kernel_size=10 )( l_embs )
conv1  = Flatten()(MaxPooling1D(pool_size=2)( conv1 ))

conv2  = Conv1D( filters=5 , kernel_size=8 )( l_embs )
conv2  = Flatten()(MaxPooling1D(pool_size=2)( conv2 ))

conv   = Concatenate()( [conv1,conv2] )
conv   = Dense(50, activation="relu")(conv)

l_out2 = Dense( len(global_labels.keys()) ,activation='softmax')(conv)

model  = Model(input=input, output=[l_out1, l_out2])
optimizer = Adam()

model.compile(optimizer=optimizer,
              loss="categorical_crossentropy",
              metrics=["accuracy"])

我想知道这里是否有人遇到过这个问题,是否有解决方案可以在训练后从模型中删除图层,更重要的是,如何在训练后重塑输入图层的大小。

谢谢

1 个答案:

答案 0 :(得分:1)

可变的时间步长不是因为使用卷积层而引起问题(实际上,关于卷积层的好处是它们不依赖于输入大小)。相反,使用Flatten层会在这里引起问题,因为它们需要指定大小的输入。相反,您可以使用全局池层。此外,我认为将卷积层和池层堆叠在一起可能会产生更好的结果,而不是使用两个单独的卷积层并将它们合并(尽管这取决于您要处理的特定问题和数据集)。因此,考虑到这两点,最好像这样编写模型:

# Global output
conv1 = Conv1D(filters=16, kernel_size=5)(l_embs)
conv1 = MaxPooling1D(pool_size=2)(conv1)

conv2 = Conv1D(filters=32, kernel_size=5)(conv1)
conv2 = MaxPooling1D(pool_size=2)(conv2)

gpool = GlobalAveragePooling1D()(conv2)

x = Dense(50, activation="relu")(gpool)
l_out2 = Dense(len(global_labels.keys()), activation='softmax')(x)

model  = Model(inputs=l_input, outputs=[l_out1, l_out2])

您可能需要调整conv + maxpool层的数量,过滤器的数量,内核大小,甚至添加辍学或批处理标准化层。

请注意,在TimeDistributed层上使用Densethe Dense layer is applied on the last axis一样是多余的。