LSTM 如何使用词嵌入进行文本分类,Keras 中的示例

yuh*_*ngd 5 machine-learning deep-learning lstm keras tensorflow

我试图了解 LSTM 如何用于对包含预训练词嵌入的文本句子(词序列)进行分类。我正在阅读有关 lstm 的一些帖子,但对详细过程感到困惑:

在 keras 上使用 LSTM 进行 IMDB 分类:https: //machinelearningmastery.com/sequence-classification-lstm-recurrent-neural-networks-python-keras/ Colah 对 LSTM 的解释:http : //colah.github.io/posts/2015- 08-了解-LSTMs/

举个例子,我想用lstm对影评进行分类,每条影评固定长度为500字。我正在使用预先训练的词嵌入(来自 fasttext),它为每个词提供 100 维向量。输入 LSTM 的 Xt 的尺寸是多少?LSTM 是如何训练的?如果每个 Xt 是一个 100 维向量代表评论中的一个词,我是否一次将评论中的每个词提供给 LSTM?LSTM 在每个 epoch 中会做什么?我真的很困惑...

来自 Colah 博客的 lstm 单元

# LSTM for sequence classification in the IMDB dataset
import numpy
from keras.datasets import imdb
from keras.models import Sequential
from keras.layers import Dense
from keras.layers import LSTM
from keras.layers.embeddings import Embedding
from keras.preprocessing import sequence
# fix random seed for reproducibility
numpy.random.seed(7)
# load the dataset but only keep the top n words, zero the rest
top_words = 5000
(X_train, y_train), (X_test, y_test) = imdb.load_data(num_words=top_words)
# truncate and pad input sequences
max_review_length = 500
X_train = sequence.pad_sequences(X_train, maxlen=max_review_length)
X_test = sequence.pad_sequences(X_test, maxlen=max_review_length)
# create the model
embedding_vecor_length = 32
model = Sequential()
model.add(Embedding(top_words, embedding_vecor_length, input_length=max_review_length))
model.add(LSTM(100))
model.add(Dense(1, activation='sigmoid'))
model.compile(loss='binary_crossentropy', optimizer='adam', metrics=['accuracy'])
print(model.summary())
model.fit(X_train, y_train, epochs=3, batch_size=64)
# Final evaluation of the model
scores = model.evaluate(X_test, y_test, verbose=0)
print("Accuracy: %.2f%%" % (scores[1]*100))
Run Code Online (Sandbox Code Playgroud)

在上面的代码示例中(摘自 Jason Brownlee 的博客https://machinelearningmastery.com/sequence-classification-lstm-recurrent-neural-networks-python-keras/),使用了 100 个单元/神经元的 LSTM。100 个神经元是如何相互连接的?为什么我不能只使用上图中的 1 个单元格进行分类,因为它是一种循环方式,因此它会在下一个时间戳将输出反馈给自身?欢迎任何可视化图表。

谢谢!!

Dan*_*ler 6

嵌入的形状:

  • 输入数据的形状:X_train.shape == (reviews, words),即(reviews, 500)

在 LSTM 中(在嵌入之后,或者如果您没有嵌入)

  • 输入数据的形状(reviews, words, embedding_size)::
    • (reviews, 500, 100) - 其中 100 是由嵌入自动创建的
  • 模型的输入形状(如果您没有嵌入层)可以是:
    • input_shape = (500, 100)
    • input_shape = (None, 100) - 此选项支持可变长度评论
  • 每个Xt都是来自 的切片input_data[:,timestep,:],这导致形状:
    • (reviews, 100)
    • 但这完全是自动的,由图层本身完成。
  • 每个都Ht被丢弃,结果只是最后一个h,因为你没有使用return_sequences=True(但这对你的模型来说没问题)。

您的代码似乎无所不能,因此您无需执行任何特殊操作即可训练此模型。使用fit适当的X_train,你会得到y_train形状(reviews,1)

问题:

如果每个 Xt 是一个 100 维向量代表评论中的一个词,我是否一次将评论中的每个词提供给 LSTM?

不,LSTM 层已经在自己做所有事情,包括所有循环步骤,只要它的输入有形状 (reviews, words, embedding_size)


100 个神经元是如何相互连接的?

它们有点平行(你可以想象 100 张像你张贴的图像一样,都是平行的),几乎与其他类型的普通图层相同。

但是在重复的步骤中,有一个 matematical 表达让他们进行对话(不幸的是我无法确切解释如何)。


为什么我不能只使用上图中的 1 个单元格进行分类,因为它是一种循环方式,因此它会在下一个时间戳将输出反馈给自身?

如果你愿意,你可以,但单元越多,层越智能(就像其他类型的层一样)

选择的数字 100 没有什么特别之处。这可能是巧合或误会。可以是任意数量,50个细胞,200个细胞,1000个细胞……


深入理解 LSTM:


nur*_*ric 5

您混淆了一些术语,让我们尝试逐步澄清正在发生的事情:

  1. 您案例中的数据将形成(样本,500),这意味着我们有一定数量的评论,每条评论最多 500 个单词编码为整数。
  2. 如果嵌入大小为 100,则该Embeddingwords[index]针对每个样本中的每个单词给出一个张量(样本,500、100)。
  3. 现在这里是一个令人困惑的地方,当我们说它LSTM(100)意味着一个层在每个输出大小为 100 的单词上运行单个LSTM 单元(如 Colah 图中的一个)。让我再试一次,你创建一个 LSTM 单元将输入转换为 100 大小的输出(隐藏大小),并且该层在单词上运行相同的单元格。
  4. 现在,我们获得(样品100),因为相同的处理LSTM 500个字每审查和返回最终输出是尺寸100的如果例如我们通过return_sequences=True在此后每隐藏输出,H-1,H,H + 1将返回图表,因此我们将获得一个形状(样本,500、100)。
  5. 最后,我们将 (samples, 100) 传递给一个Dense层以进行预测,从而给出 (samples, 1) 因此对批次中的每个评论进行预测。

吸取的教训是,该LSTM 环绕LSTMCell并为您在每个时间步长上运行它,因此您不必自己编写循环操作。