Skip to content

词嵌入近似训练

一、为什么需要近似训练

之前我们学的跳元模型(用中心词预测周围词)和连续词袋模型(用周围词预测中心词),在计算梯度的时候,都需要对整个词表的所有词进行求和计算。但实际里词表往往有几十万甚至上百万个词,这样的计算量太大了,根本没法高效训练。所以就需要用近似训练的方法,来降低计算复杂度.

主要有两种方法:负采样和分层 softmax

二、负采样:把多分类变成二分类

1. 基本思路

原来的跳元模型是一个多分类问题:给定中心词,要预测它的上下文词是词表里的哪一个,需要计算每个词的概率。负采样把这个问题改成了二分类问题:

  • 正样本:中心词和它上下文里的词,这个组合是 “真的上下文对”,用 sigmoid 函数计算这个事件的概率,sigmoid 函数可以把两个词向量的点积转换成 0 到 1 之间的概率值,点积越大,概率越接近 1,说明这两个词越可能是上下文对。
  • 负样本:从词表里随机选 K 个不是上下文里的词(叫噪声词),这些组合是 “假的上下文对”,同样用 sigmoid 函数计算这些组合是假的概率。

2. 损失函数

我们的目标是让正样本的概率尽可能大,负样本的概率尽可能小。对应的损失函数就是:对于每个正样本,我们要最大化它是真的概率;对于每个负样本,我们要最大化它是假的概率。把这些概率取对数加起来,再取负数,就得到了损失函数,这样我们就可以用梯度下降来最小化这个损失。

3. 计算量的优势

原来的计算量和词表大小成正比,现在负采样的计算量只和我们选的噪声词数量 K 成正比,K 一般选很小的数(比如 5-20),这样计算量就大大减少了。

三、分层 softmax:用二叉树简化计算

用于近似训练的分层softmax,其中树的每个叶节点表示词表中的一个词

1. 基本思路

分层 softmax 把词表里的每个词都作为二叉树的叶子节点,每个非叶子节点都有一个向量。这样,计算给定中心词生成某个上下文词的概率,就变成了从二叉树的根节点走到这个词对应的叶子节点的过程,每一步走左子树或者右子树的概率用 sigmoid 函数计算,最后把路径上的所有概率乘起来,就是这个词的条件概率。

2. 举个例子

比如我们有一个二叉树,根节点是 N1,左子节点是 N2,右子节点是 w1;N2 的左子节点是 w2,右子节点是 w3。要计算中心词生成 w3 的概率,就是从根节点 N1 走到 w3 的路径:先从 N1 走到 N2(计算这个步骤的概率),再从 N2 走到 w3(计算这个步骤的概率),把这两个概率乘起来,就是 w3 的条件概率。

3. 计算量的优势

二叉树里,从根到叶子的路径长度大概是词表大小的对数(比如词表有 100 万个词,对数大概是 20),所以计算量就从原来的和词表大小成正比,变成了和词表大小的对数成正比,大大减少了计算量。

四、小结

  1. 负采样把多分类问题转成二分类,通过正样本和随机选的负样本计算损失,计算量和噪声词数量 K 成正比,K 很小的时候计算很快。

  2. 分层 softmax 用二叉树来表示词表,把条件概率变成路径上的概率乘积,计算量和词表大小的对数成正比,适合词表很大的场景。

  3. 这两种方法都是为了降低词嵌入训练的计算量,让大词表的词嵌入训练变得可行。

五、练习

  1. 负采样里的噪声词怎么选?

一般是按照词的出现频率来采样,出现频率高的词被选中的概率更大。

  1. 验证分层 softmax 的所有词的条件概率加起来是 1

因为二叉树的每个路径都是互斥的,所有叶子节点的路径概率加起来就是 1,所以所有词的条件概率总和是 1。

  1. 怎么用负采样和分层 softmax 训练连续词袋模型?

思路和跳元模型类似,连续词袋模型是用周围词预测中心词,负采样就是把周围词和中心词作为正样本,选噪声词作为负样本;分层 softmax 就是把中心词作为目标,用二叉树的路径来计算概率。

(注:文档部分内容可能由 AI 生成) 源地址

京ICP备2024093538号-1