Keras嵌入层:它们如何工作?

问题描述 投票:7回答:3

我开始使用Keras构建神经网络模型。

我有一个分类问题,其中的功能是离散的。为了管理这种情况,标准过程包括使用单热编码转换二进制数组中的离散特征。

然而,似乎使用Keras这一步骤不是必需的,因为可以简单地使用嵌入层来创建这些离散特征的特征向量表示。

这些embeddings是如何进行的?

我的理解是,如果离散特征f可以假设k值,那么嵌入层创建一个带有k列的矩阵。每次我收到该特征的值,比如i,在训练阶段,只会更新矩阵的i列。

我的理解是否正确?

python machine-learning neural-network keras embedding
3个回答
4
投票

人们可能很容易注意到 - one-hot向量与Embedding矩阵的乘法可以在恒定时间内有效地执行,因为它可以被理解为矩阵切片。这正是Embedding层在计算过程中所做的。它只是使用gather后端函数选择适当的索引。这意味着您对Embedding图层的理解是正确的。


2
投票

假设您有N个对象没有直接具有数学表示。例如单词。

由于神经网络只能与张量一起使用,因此您应该寻找某种方法将这些对象转换为张量。解决方案是在一个巨大的矩阵(嵌入矩阵)中,它将一个对象的每个索引与其转换为张量相关联。

object_index_1: vector_1
object_index_1: vector_2
...
object_index_n: vector_n

选择特定对象的矢量可以通过以下方式转换为矩阵产品:

enter image description here

其中v是确定需要翻译哪个单词的单热矢量。 M是嵌入矩阵。

如果我们提出通常的管道,那将是以下内容:

  1. 我们有一个对象列表。
objects = ['cat', 'dog', 'snake', 'dog', 'mouse', 'cat', 'dog', 'snake', 'dog']
  1. 我们将这些对象转换为索引(我们计算唯一对象)。
unique = ['cat', 'dog', 'snake', 'mouse'] # list(set(objects))
objects_index = [0, 1, 2, 1, 3, 0, 1, 2, 1] #map(unique.index, objects)

  1. 我们将这些索引转换为一个热矢量(请记住索引只有一个)
objects_one_hot = [[1, 0, 0, 0], [0, 1, 0, 0], [0, 0, 1, 0], [0, 1, 0, 0], 
     [0, 0 , 0, 1], [1, 0, 0, 0], [0, 1, 0, 0], [0, 0, 1, 0], [0, 1, 0, 0]] # map(lambda x: [int(i==x) for i in range(len(unique))], objects_index)
#objects_one_hot is matrix is 4x9
  1. 我们创建或使用嵌入矩阵:
#M = matrix of dim x 4 (where dim is the number of dimensions you want the vectors to have). 
#In this case dim=2
M = np.array([[1, 1], [1, 2], [2, 2], [3,3]]).T # or... np.random.rand(2, 4)
#objects_vectors = M * objects_one_hot
objects_vectors = [[1, 1], [1, 2], [2, 2], [1, 2], 
    [3, 3], [1, 1], [1, 2], [2,2], [1, 2]] # M.dot(np.array(objects_one_hot).T)

通常,在相同的模型学习期间学习嵌入矩阵,以适应每个对象的最佳向量。我们已经有了对象的数学表示!

如您所见,我们使用了一种热和后来的矩阵产品。你真正做的是取M代表那个词的列。

在学习期间,M将被调整以改善对象的表示,结果损失减少。


1
投票

Keras中的嵌入层(通常也是)是一种创建密集字编码的方法。您应该将其视为矩阵乘以单热编码(OHE)矩阵,或简单地作为OHE矩阵上的线性层。

它始终用作直接连接到输入的图层。

稀疏和密集的字编码表示编码有效性。

单热编码(OHE)模型是稀疏字编码模型。例如,如果我们有1000个输入激活,则每个输入要素将有1000个OHE向量。

假设我们知道一些输入激活是依赖的,我们有64个潜在的特征。我们有这个嵌入:

e = Embedding(1000, 64, input_length=50)

1000告诉我们计划总共编码1000个单词。 64告诉我们使用64维向量空间。 50告诉输入文件每个有50个单词。

嵌入图层将随机填充非零值,并且需要学习参数。

here中创建嵌入层时还有其他参数

嵌入层的输出是什么?

嵌入层的输出是2D向量,在输入的单词序列(输入文档)中为每个单词嵌入一个。

注意:如果要将Dense图层直接连接到嵌入图层,必须先使用Flatten layer将2D输出矩阵展平为1D向量。

© www.soinside.com 2019 - 2024. All rights reserved.