目录
- skip gram神经网络体系结构模型
- 负采样
skip gram神经网络体系结构
模型
Word2Vec使用了在机器学习的其他地方见过的技巧。我们将构建一个监督学习任务的神经网络,它只有一个隐藏层,我们的目标实际上只是学习隐藏层的权重——我们将看到这些权重实际上是我们要学习的“单词向量”(word vectors),而学到权重之后,用于将单词特征化表示
“伪”任务
我们要训练神经网络做以下事情。给定一个位于句子中间的特定单词(输入单词),并在其附近(nearby)单词随机选择一个。这个网络会告诉我们,我们词汇表中的每个单词是选择的“邻近单词”的概率。
(网络的)输出概率反映了词汇表中的每个单词是在输入词附近的可能性。
例如,如果你给训练好的网络输入单词“Soviet”,像“Union”和“Russia”这样的单词的输出概率要比像“watermelon”和“kangaroo”这样的不相关的单词高得多(输出概率值大)。
通过训练文档中找到的单词对(word pairs)来训练神经网络,每一个单词对代表训练样本x和对应的标签y。
下面的例子显示了我们将从“The quick brown fox jumps over the lazy dog”这句话中提取的一些训练样本。用蓝色高亮显示的单词是输入单词。
网络将从每对单词出现的次数中学习统计数据。
例如,网络可能会得到更多的单词对(“Soviet”,“Union”),而不是(“Soviet”,“Sasquatch”)单词对。
当训练结束时,如果把“Soviet”这个单词作为输入,那么输出“Union”或“Russia”的概率将比输出“Sasquatch”的概率高得多
模型细节
首先,你知道你不能将一个单词作为文本字符串输入到神经网络,所以我们需要一种方法来将单词表示到网络中
我们首先从训练文档中构建词汇表——假设我们有10,000个唯一的单词,我们要把一个像“ant”这样的输入词表示成一个one_hot向量
训练网络时,每个输入词以one_hot向量表示,每个输出词也是one_hot向量表示
网络的输出是单个向量(也包含10,000个分量),代表词汇表中的每个单词是nearby随机选择概率
隐层神经元没有激活功能.
但是当你在一个输入词上评估(evaluate )已训练的网络时,输出向量实际上是一个概率分布(softmax分类器输出一堆浮点值,而不是一个one_hot向量)。
隐藏层
在我们的例子中,我们说我们正在学习具有300个特征的单词向量(word vectors), 因此,隐含层将由一个权重矩阵表示,该矩阵形状是(10,000,300)
Google 在其发布的模型中使用了300个特性,并在Google news数据集上进行了训练。特征数量是一个“超参数”,您只需对您的应用程序进行调优(也就是说,尝试不同的值,看看什么会产生最佳结果)。
权重矩阵的行,就是词向量
所以所有这些的最终目标实际上只是学习这个隐藏层权重矩阵——最后将丢弃输出层!
回到模型定义
模型的隐藏层实际上只是作为一个查找表来操作
输入:one_hot向量
线性运算:dot(one_hot, Weight)
输出:词向量
输出层
然后,代表“ants”的1 x 300词向量被输入到输出层,输出层是softmax分类器,每个输出神经元(我们词汇表中的每个单词都有一个)将产生0到1之间的输出,所有这些输出值的和将加起来等于1
每个输出神经元都有一个权重,它与隐含层输出的词向量相乘,然后对结果应用exp(x)
函数。最后,为了使输出之和达到1,我们将这个结果除以来自所有10,000个输出节点的结果之和。
下图代表输入词ant,输出为”car“的概率
如果"car"在ant附近,那么这个神经元的输出概率将很高,否则将很低
直觉
如果两个不同的单词有非常相似的“上下文”,那么我们的模型需要为这两个单词输出非常相似的结果。
网络输出这两个单词相似的上下文预测的一种途径是两个词向量是相似的(两个单词的特征向量相似,那么输出结果是相似的)。所以,如果两个单词有相似的上下文,那么我们的网络就会有动力为这两个单词学习相似的单词向量(特征向量)!
两个词有相似的上下文是什么意思?
像“intelligent”和“smart”这样的同义词会有非常相似的上下文。或者相关的词,比如“engine”和“transmission”,可能也有类似的上下文。这也可以为您处理词干分析(stemming )——网络可能会为单词“ant”和“ants”学习相似的单词向量,因为它们应该具有相似的上下文。
skip-gram神经网络包含了大量的权值……对于我们的例子来说,300个特征和10000个单词的词汇量,在隐含层和输出层各有3M的权值!在大型数据集上进行训练是不可能的,word2vec的作者引入了一些调整,这些调整对于实际训练是非常重要的
负采样
上面所说的神经网络有两个权重矩阵——隐藏层和输出层。这两层都有一个300 x 10000 = 300万的权重矩阵
在这么大的神经网络上运行梯度下降会很慢。更糟的是,你需要大量的训练数据来调整那么多的重量避免overfiting。数百万的权重乘以数十亿的训练样本意味着训练这个模型将是一头野兽。
Word2Vec的作者在他们的第二篇论文中解决了这些问题,并进行了以下两个创新:
对频繁出现的单词进行二次抽样,减少训练样本数量
用“负抽样”修改优化目标,这使得每个训练样本只更新模型权重的一小部分。
值得注意的是,对高频词进行二次抽样和负采样,不仅减少了训练过程的计算负担,而且提高了生成的词向量的质量
对高频词二次采样
像“the”这样的常用词有两个“问题”:
像这样的单词对(“fox”,“the”)并没有告诉我们多少关于“fox”的意思。“the”出现在几乎每个单词的上下文中。
像这样的样本(“the”, …)比我们需要学习的“the”的好的词向量多得多
Word2Vec实现了一个“二次抽样”方案来解决这个问题。对于我们在训练文本中遇到的每一个单词,我们都有可能将其有效地从文本中删除。删除这个词的可能性与这个词的频率有关
如果我们的窗口大小为10,我们从文本中删除一个特定的“the”实例,这将导致:
- 当我们训练剩下的单词时,“the”将不会出现在它们的任何上下文中。——解决问题1
- 以“the"作为输入词的样本数将减少10个——解决问题2
负采样
每个训练样本都会调整神经网络中的所有权重。
正如我们在上面讨论过的,单词词汇量的大小意味着我们的skip-gram神经网络有大量的权重,所有这些权重都会被我们数十亿个训练样本中的每一个略微更新!负采样通过让每个训练样本只修改一小部分权重来解决这个问题,而不是全部。
原理:
训练网络上的单词对(“fox”、“quick”)时,对应于“quick”的输出神经元将输出1,对于所有其他数千个输出神经元输出0。(label是一个one_hot)
对于负采样,我们将随机选择少量的“negative”词来更新权重。(在此上下文中,“negative”词是指我们希望网络为其输出为0)。我们还将更新“positive”词的权重。
回想一下,我们模型的输出层有一个300 x 10000的权值矩阵,所以我们只需要更新我们的positive单词的权重,加上我们想输出0的其他5个单词的权重。这样总共就只有6个输出神经元,1800个权重值。这只是输出层300万权重的0.06% !
在隐藏层中,只更新输入单词的权重(无论是否使用负抽样)
选择负样本
“负样本”(即我们将训练输出0的5个输出单词)使用“unigram分布”进行选择,其中高频单词更有可能被选择为负样本。
例如,假设你有一个完整的训练语料库作为单词列表,你从列表中随机抽取5个负样本。在这种情况下,选择单词“couch”的概率将等于“couch”出现在语料库中的次数,除以语料库中单词总数
作者在他们的论文中说,他们尝试了这个方程的一些变化,其中表现最好的是把字数提高到3/4次方:
这个方程倾向于增加低频单词的概率和减少高频单词的概率,使得高频单词(像"the"之类的)更可能作为负样本,而低频单词不会被选择作为负样本。
Word Pairs and “Phrases”
略