如何正确使用 mask_zero=True 进行预训练权重的 Keras 嵌入?

Ast*_*Ben 5 python keras tensorflow word-embedding

我很困惑如何格式化我自己预先训练的权重为KerasEmbedding层,如果我还设置mask_zero=True。这是一个具体的玩具示例。

假设我有 4 个单词的词汇表,[1,2,3,4]并且正在使用由以下定义的向量权重:

weight[1]=[0.1,0.2]
weight[2]=[0.3,0.4]
weight[3]=[0.5,0.6]
weight[4]=[0.7,0.8]
Run Code Online (Sandbox Code Playgroud)

我想嵌入长度不超过 5 个单词的句子,所以我必须在将它们输入到嵌入层之前对它们进行零填充。我想掩盖零,以便进一步的图层不使用它们。

阅读用于嵌入的 Keras 文档,它说 0 值不能出现在我的词汇表中。

mask_zero:输入值 0 是否是应屏蔽的特殊“填充”值。这在使用可能需要可变长度输入的循环层时很有用。如果为 True,则模型中的所有后续层都需要支持屏蔽,否则将引发异常。如果 mask_zero 设置为 True,结果,索引 0 不能在词汇表中使用(input_dim 应等于词汇表的大小 + 1)。

所以我感到困惑的是如何为嵌入层构造权重数组,因为“索引 0 不能在词汇表中使用”。如果我将权重数组构建为

[[0.1,0.2],
 [0.3,0.4],
 [0.5,0.6],
 [0.7,0.8]]
Run Code Online (Sandbox Code Playgroud)

那么通常情况下, word1会指向索引 1,在这种情况下,它保存 word 的权重2。还是当您指定时mask_zero=True,Keras 内部会使其1指向索引 0?或者,您是否只是在索引零中添加一个零向量,如下所示?

[[0.0,0.0],
 [0.1,0.2],
 [0.3,0.4],
 [0.5,0.6],
 [0.7,0.8]]
Run Code Online (Sandbox Code Playgroud)

在我看来,第二个选项是将零放入词汇表中。换句话说,我很困惑。任何人都可以阐明这一点吗?

mod*_*itt 6

你的第二种方法是正确的。您将需要按以下方式构建嵌入层

embedding = Embedding(
   output_dim=embedding_size,
   input_dim=vocabulary_size + 1,
   input_length=input_length,
   mask_zero=True,
   weights=[np.vstack((np.zeros((1, embedding_size)),
                       embedding_matrix))],
   name='embedding'
)(input_layer)
Run Code Online (Sandbox Code Playgroud)

embedding_matrix您提供的第二个矩阵在哪里。

您可以通过查看keras 嵌入层的实现来看到这一点。值得注意的是, mask_zero 仅用于字面屏蔽输入

def compute_mask(self, inputs, mask=None):
    if not self.mask_zero:
        return None
    output_mask = K.not_equal(inputs, 0)
    return output_mask
Run Code Online (Sandbox Code Playgroud)

因此,整个内核仍然乘以输入,这意味着所有索引都向上移动 1。