在浅谈词嵌入(一)中我们曾说过,在没有词嵌入矩阵之前我们想要将一个单词编码成计算机可识别的形式一般采用的是one-hot编码。而在有了词嵌入矩阵后我们可以利用词嵌入矩阵中的一系列特征更好地表示单词,那么词嵌入矩阵是怎么得来的呢?
词嵌入矩阵实际也是学习得到的,如同大多数模型一样,只不过大多数模型学习得到的是一个分类器,而词嵌入矩阵则是取模型的参数。下面我们简单的了解词嵌入矩阵的学习。
1、从简单的神经网络模型说起
在上面我们说到词嵌入矩阵其实是学习模型时所得到的参数,那么我们就可以通过神经网络建立一个语言模型来学习词嵌入矩阵。
现在假设我们要使用神经网络来建立一个语言模型,这个语言模型的输入是一个不完整的句子,我们要学习模型的目的便是要预测模型中缺了的那个句子是什么。假设这个句子为“I want a glass of orange juice”,现在juice是缺失的,如下图:
在将句子输入神经网络之前,依然是先将其转化为一个one-hot向量,向量长度即词典长度。这些one-hot向量先经过一个隐藏层(上图中的E代表隐藏层的参数矩阵),再经过softmax得到输出,输出向量长度等于词典大小,输出向量中的每个概率等于词典中每个词为预测结果的概率。
我们只需要一个语料库,然后将这些句子放入上面的神经网络中进行训练便可以得到一个语言模型,其中这个语言模型的隐藏层的参数矩阵E便是我们需要的词嵌入矩阵。
上面的模型看起来可行而且非常简单,但是有一个重要的问题——输出层的softmax计算量非常大,加入一个词典大小为10000,那么这个softmax层便需要计算10000个值,这个计算量是非常大的,非常花费时间。而word2vec中的cbow和skip-gram方法便是对softmax层进行了优化,大大减少了计算量,下面我们进行简单的了解。
2、利用word2vec训练词嵌入矩阵
在word2vec中有两种训练词嵌入矩阵的方法——CBOW和skip-gram。cbow和skip-gram算法如下图所示,cbow是利用一段语句的上下文词语去预测其中心词,而skip-gram则是通过中心词来预测其上下文的词语。
上图给出了word2vec中两个模型的算法,但是仅仅如此还不够,这样会遇到与上面讲到的普通神经网络语言模型的问题——计算量太大,所以在word2vec中使用了两种方式来减少计算量:基于霍夫曼树的层次softmax和负采样技术。此外,需要提一下的是,word2vec中输入经过隐藏层时没有常见的非线性激活而是简单的求平均。
下面的Hierarchical Softmax和负采样均转自https://www.cnblogs.com/pinard/p/7243513.html.
2.1 基于Hierarchical Softmax的模型
为了避免要计算所有词的softmax概率,word2vec采样了霍夫曼树来代替从隐藏层到输出softmax层的映射。如何映射呢?这里就是理解word2vec的关键所在了。不过在讲Hierarchical Softmax之前不妨先了解一下霍夫曼树。
2.1.1 霍夫曼树
霍夫曼树的建立其实并不难,过程如下:
输入:权值为(𝑤1,𝑤2,...𝑤𝑛)的𝑛个节点
输出:对应的霍夫曼树
1)将(𝑤1,𝑤2,...𝑤𝑛)看做是有𝑛棵树的森林,每个树仅有一个节点。
2)在森林中选择根节点权值最小的两棵树进行合并,得到一个新的树,这两颗树分布作为新树的左右子树。新树的根节点权重为左右子树的根节点权重之和。
3) 将之前的根节点权值最小的两棵树从森林删除,并把新树加入森林。
4)重复步骤2)和3)直到森林里只有一棵树为止。
下面我们用一个具体的例子来说明霍夫曼树建立的过程,我们有(a,b,c,d,e,f)共6个节点,节点的权值分布是(20,4,8,6,16,3)。
首先是最小的b和f合并,得到的新树根节点权重是7.此时森林里5棵树,根节点权重分别是20,8,6,16,7。此时根节点权重最小的6,7合并,得到新子树,依次类推,最终得到下面的霍夫曼树。
那么霍夫曼树有什么好处呢?一般得到霍夫曼树后我们会对叶子节点进行霍夫曼编码,由于权重高的叶子节点越靠近根节点,而权重低的叶子节点会远离根节点,这样我们的高权重节点编码值较短,而低权重值编码值较长。这保证的树的带权路径最短,也符合我们的信息论,即我们希望越常用的词拥有更短的编码。如何编码呢?一般对于一个霍夫曼树的节点(根节点除外),可以约定左子树编码为0,右子树编码为1.如上图,则可以得到c的编码是00。
在word2vec中,约定编码方式和上面的例子相反,即约定左子树编码为1,右子树编码为0,同时约定左子树的权重小于右子树的权重。
2.1.2 Hierarchical Softmax
为了避免要计算所有词的softmax概率,word2vec采样了霍夫曼树来代替从隐藏层到输出softmax层的映射。我们在上一节已经介绍了霍夫曼树的原理。如何映射呢?这里就是理解word2vec的关键所在了。
由于我们把之前所有都要计算的从输出softmax层的概率计算变成了一颗二叉霍夫曼树,那么我们的softmax概率计算只需要沿着树形结构进行就可以了。如下图所示,我们可以沿着霍夫曼树从根节点一直走到我们的叶子节点的词𝑤2。
和之前的神经网络语言模型相比,我们的霍夫曼树的所有内部节点就类似之前神经网络隐藏层的神经元,其中,根节点的词向量对应我们的投影后的词向量,而所有叶子节点就类似于之前神经网络softmax输出层的神经元,叶子节点的个数就是词汇表的大小。在霍夫曼树中,隐藏层到输出层的softmax映射不是一下子完成的,而是沿着霍夫曼树一步步完成的,因此这种softmax取名为"Hierarchical Softmax"。
如何“沿着霍夫曼树一步步完成”呢?在word2vec中,我们采用了二元逻辑回归的方法,即规定沿着左子树走,那么就是负类(霍夫曼树编码1),沿着右子树走,那么就是正类(霍夫曼树编码0)。判别正类和负类的方法是使用sigmoid函数,即:
其中𝑥𝑤是当前内部节点的词向量,而𝜃则是我们需要从训练样本求出的逻辑回归的模型参数。
使用霍夫曼树有什么好处呢?首先,由于是二叉树,之前计算量为𝑉,现在变成了𝑙𝑜𝑔2𝑉。第二,由于使用霍夫曼树是高频的词靠近树根,这样高频词需要更少的时间会被找到,这符合我们的贪心优化思想。
容易理解,被划分为左子树而成为负类的概率为𝑃(−)=1−𝑃(+)。在某一个内部节点,要判断是沿左子树还是右子树走的标准就是看𝑃(−),𝑃(+)谁的概率值大。而控制𝑃(−),𝑃(+)谁的概率值大的因素一个是当前节点的词向量,另一个是当前节点的模型参数𝜃。
对于上图中的𝑤2,如果它是一个训练样本的输出,那么我们期望对于里面的隐藏节点𝑛(𝑤2,1)的𝑃(−)概率大,𝑛(𝑤2,2)的𝑃(−)概率大,𝑛(𝑤2,3)的𝑃(+)概率大。
回到基于Hierarchical Softmax的word2vec本身,我们的目标就是找到合适的所有节点的词向量和所有内部节点𝜃, 使训练样本达到最大似然。那么如何达到最大似然呢?先拿上面的𝑤2例子来看,我们期望最大化下面的似然函数:
对于所有的训练样本,我们期望最大化所有样本的似然函数乘积。更详细的关于基于Hierarchical Softmax的模型梯度计算参见# word2vec原理(二) 基于Hierarchical Softmax的模型。
2.2 Negative Sampling
在讲基于Negative Sampling的word2vec模型前,我们先看看Hierarchical Softmax的的缺点。的确,使用霍夫曼树来代替传统的神经网络,可以提高模型训练的效率。但是如果我们的训练样本里的中心词𝑤是一个很生僻的词,那么就得在霍夫曼树中辛苦的向下走很久了。能不能不用搞这么复杂的一颗霍夫曼树,将模型变的更加简单呢?
Negative Sampling就是这么一种求解word2vec模型的方法,它摒弃了霍夫曼树,采用了Negative Sampling(负采样)的方法来求解,下面我们就来看看Negative Sampling的求解思路。
2.2.1 基于Negative Sampling的模型概述
既然名字叫Negative Sampling(负采样),那么肯定使用了采样的方法。采样的方法有很多种,比如之前讲到的大名鼎鼎的MCMC。我们这里的Negative Sampling采样方法并没有MCMC那么复杂。
比如我们有一个训练样本,中心词是𝑤,它周围上下文共有2𝑐个词,记为𝑐𝑜𝑛𝑡𝑒𝑥𝑡(𝑤)。由于这个中心词𝑤,的确和𝑐𝑜𝑛𝑡𝑒𝑥𝑡(𝑤)相关存在,因此它是一个真实的正例。通过Negative Sampling采样,我们得到neg个和𝑤不同的中心词𝑤𝑖,𝑖=1,2,..𝑛𝑒𝑔,这样𝑐𝑜𝑛𝑡𝑒𝑥𝑡(𝑤)和𝑤𝑖就组成了neg个并不真实存在的负例。利用这一个正例和neg个负例,我们进行二元逻辑回归,得到负采样对应每个词𝑤𝑖对应的模型参数𝜃𝑖,和每个词的词向量。
从上面的描述可以看出,Negative Sampling由于没有采用霍夫曼树,每次只是通过采样neg个不同的中心词做负例,就可以训练模型,因此整个过程要比Hierarchical Softmax简单。
不过有两个问题还需要弄明白:1)如果通过一个正例和neg个负例进行二元逻辑回归呢? 2) 如何进行负采样呢?
对于问题(1):
相当于对k个负例和1个正例分别进行逻辑回归,然后得到一个最大化似然函数,即:
对于问题(2):
一个办法是对中间的这些词进行采样,即候选的目标
词,你可以根据其在语料中的经验频率进行采样,就是通过词出现的频率对其进行采样。但问题是这会导致你在 like、 the、 of、 and 诸如此类的词上有很高的频率。另一个极端就是用1 除以词汇表总词数,即 1/|𝑣|,均匀且随机地抽取负样本,这对于英文单词的分布是非常没有代表性的。所以论文的作者Mikolov 等人根据经验采用的采样方法位于这两个极端的采样方法之间,既不用经验频率,也就是实际观察到的英文文本的分布,也不用均匀分布,他们采用以下方式:
𝑓(𝑤𝑖)是观测到的在语料库中的某个英文词的词频,通过3/4次方的计算,使其处于完全独立的分布和训练集的观测分布两个极端之间。虽然目前似乎尚未有理论证明,但是很多研究者现在使用这个方法,似乎也效果不错。
3、小结
将两种优化算法与前面的两个模型组合,在Google的论文里一共包含了4种Word2Vec的实现。
- Hierarchical Softmax CBOW 模型
- Hierarchical Softmax Skip-Gram 模型
- Negative Sampling CBOW 模型
- Negative Sampling Skip-Gram 模型
一般来说,cbow模型可能对小的语料库的效果更好,而skip-gram则对于大语料库效果更好。
参考:
深度学习. 吴恩达
word2vec原理(一) CBOW与Skip-Gram模型基础
word2vec原理(二) 基于Hierarchical Softmax的模型
word2vec原理(三) 基于Negative Sampling的模型