我正在学习tensorflow2.0并遵循tutorial。在rnn
示例中,我找到了代码:
def build_model(vocab_size, embedding_dim, rnn_units, batch_size):
model = tf.keras.Sequential([
tf.keras.layers.Embedding(vocab_size, embedding_dim,
batch_input_shape=[batch_size, None]),
tf.keras.layers.LSTM(rnn_units,
return_sequences=True,
stateful=True,
recurrent_initializer='glorot_uniform'),
tf.keras.layers.Dense(vocab_size)
])
return model
我的问题是:为什么代码设置了参数return_sequences=True
和stateful=True
?如何使用默认参数?
答案 0 :(得分:2)
教程中的示例与文本生成有关。这是批量输入网络的输入:
(64,100,65)#(batch_size,sequence_length,vocab_size)
return_sequences=True
由于打算在每个时间步长(即序列中的每个字符)预测一个字符,因此需要预测下一个字符。
因此,将参数return_sequences=True
设置为true,以获得(64,100,65)的输出形状。如果将此参数设置为False,则仅返回最后一个输出,因此对于64批,输出将为(64,65),即对于每100个字符的序列,仅返回最后的预测字符。>
stateful=True
从文档中, “如果为True,则批次中索引i的每个样本的最后状态将用作下一批批次中索引i的初始状态。”
在该教程的下图中,您可以看到设置有状态有助于LSTM通过提供先前预测的上下文来做出更好的预测。
答案 1 :(得分:2)
让我们看一下使用LSTM构建的典型模型体系结构。
我们输入一系列输入(x),一次输入一批,每个LSTM单元返回一个输出(y_i)。因此,如果您输入的大小为batch_size x time_steps X input_size
,则LSTM输出将为batch_size X time_steps X output_size
。这称为序列到序列模型,因为输入序列被转换为输出序列。该模型的典型用法是在标记器(POS标记器,NER Tagger)中。在keras中,这可以通过设置return_sequences=True
来实现。
在多对一架构中,我们仅使用最后一个LSTM单元的输出状态。这种体系结构通常用于分类问题,例如预测电影评论(表示为单词序列)是否为-ve的-ve。在keras中,如果我们设置return_sequences=False
,则模型仅返回最后一个LSTM单元的输出状态。
LSTM单元由许多门组成,如下图from所示。前一个单元的状态/门用于计算当前单元的状态。在keras中,如果statefull=False
,则每批处理后都会重置状态。如果statefull=True
来自索引i
的上一批次的状态将用作下一批次中索引i
的初始状态。因此状态信息将在statefull=True
之间在批次之间传播。选中此link,以获取有关示例示例的状态充满性说明。
答案 2 :(得分:1)
让我们看看使用参数时的区别:
tf.keras.backend.clear_session()
tf.set_random_seed(42)
X = np.array([[[1,2,3],[4,5,6],[7,8,9]],[[1,2,3],[4,5,6],[0,0,0]]], dtype=np.float32)
model = tf.keras.Sequential([tf.keras.layers.LSTM(4, return_sequences=True, stateful=True, recurrent_initializer='glorot_uniform')])
print(tf.keras.backend.get_value(model(X)).shape)
# (2, 3, 4)
print(tf.keras.backend.get_value(model(X)))
# [[[-0.16141939 0.05600287 0.15932009 0.15656665]
# [-0.10788933 0. 0.23865232 0.13983202]
[-0. 0. 0.23865232 0.0057992 ]]
# [[-0.16141939 0.05600287 0.15932009 0.15656665]
# [-0.10788933 0. 0.23865232 0.13983202]
# [-0.07900514 0.07872108 0.06463861 0.29855606]]]
因此,如果将return_sequences
设置为True
,则模型将返回它预测的完整序列。
tf.keras.backend.clear_session()
tf.set_random_seed(42)
model = tf.keras.Sequential([
tf.keras.layers.LSTM(4, return_sequences=False, stateful=True, recurrent_initializer='glorot_uniform')])
print(tf.keras.backend.get_value(model(X)).shape)
# (2, 4)
print(tf.keras.backend.get_value(model(X)))
# [[-0. 0. 0.23865232 0.0057992 ]
# [-0.07900514 0.07872108 0.06463861 0.29855606]]
因此,如文档所述,如果将return_sequences
设置为False
,则模型仅返回最后的输出。
对于stateful
来说,要深入一点比较困难。但从本质上讲,它的作用是在有多批输入时,批i
的最后一个单元状态将是批i+1
的初始状态。但是,我认为使用默认设置会更好。