语言模型
统计语言模型是一个单词序列上的概率分布,对于一个给定长度为m的序列,它可以为整个序列产生一个概率 P(w_1,w_2,…,w_m) 。其实就是想办法找到一个概率分布,它可以表示任意一个句子或序列出现的概率。
语言模型实例:通过联合分布将词语间的先后顺序表示出来,一句话的新出现的词语都是建立在之前的词语的基础上的
p(S)=p(w1,w2,w3,w4,w5,…,wn) = p(w1)p(w2|w1)p(w3|w1,w2)…p(wn|w1,w2,…,wn-1)
p(S)被称为语言模型,即用来计算一个句子概率的模型
缺点:
- 数据稀疏性:不是每一个词都会组合在一起的,出现的概率很低,这样构造出了非常多的词对,但实际中训练语料是不会出现这么多种组合的
- 参数空间太大:数据的稀疏性,模型的自由参数是随着字符串长度的增加而指数级暴增的,这使我们几乎不可能正确的估计出这些参数
N-gram模型
参数N表示下一个出现的词与前面N个词相关
一个词会和它附近的词联系比较紧密,那我们就可以简化语言模型的概率公式,假设下一个词的出现依赖它前面的两个词:
p(S)=p(w1)p(w2|w1)p(w3|w1,w2)…p(wn|w1,w2,…,wn-1)
=p(w1)p(w2|w1)p(w3|w1,w2)…p(wn|wn-1,wn-2)
从语料库中统计了每个词出现的次数
我们假设N=1,则词语 i 的下一个词为i、want、to…的次数分别记在表中
例如 i 之后的词为want的概率为:p=want在i之后出现的次数/i出现的次数=0.33
所以一句话出现的概率可以这样计算:
下面计算一下N-gram模型的复杂度:
假设语料库的大小为1000个词,现要统计某个单词前两个的词的相关性,则复杂为O(1000^2),所以要统计某个单词前 n 个的词的相关性,n个词的相关性则为O(1000^n)
词向量
常用的词表示方法是 One-hot Representation,这种方法把每个词表示为一个很长的向量。这个向量的维度是词表大小,其中绝大多数元素为 0,只有一个维度的值为 1,这个维度就代表了当前的词。
举个栗子,
“话筒”表示为 [0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 …]
“麦克”表示为 [0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 …]
这种表示方法也存在一个重要的问题就是“词汇鸿沟”现象:任意两个词之间都是孤立的。光从这两个向量中看不出两个词是否有关系,哪怕是话筒和麦克这样的同义词也不能幸免于难
Deep Learning用Distributed Representation表示的一种低维实数向量。这种向量一般长成这个样子:[0.792, −0.177, −0.107, 0.109, −0.542, …]。维度以 50 维和 100 维比较常见
优点:
- 计算机能够方便理解语义的相似性
- 只要语言逻辑相近,能适用与不同语言
词义相近的词词向量也相近:
词向量在不同语言中也是更为方便,更关注的是上下文的逻辑,而不是关注词是怎么写的,相近词义的词语都会有相似的词向量,方便计算机理解
神经网络模型
- 输入:我今天下午打(向量形式)
- 预测:篮球(打什么东西)
- 训练样本:
包括前 n-1 个词分别的向量,假定每个词向量大小m - 投影层: (n-1)*m 首尾拼接起来的大向量(将输入的词建立一个关系)
- 输出:
表示上下文为 时,下一个词恰好为词典中第i个词的概率(给词打标签,再进行loss的优化,调节权重参数) - 归一化:
神经网络的优势
对于预测“网咖”,“网吧”在统计中,网咖出现的次数较多,一般会预测成”网咖‘
而在神经网络模型中,是根据词向量来进行预测,两个词的词义相同,所以出现的概率也相同
所以神经网络模型对于语义相近句子会认为是相同的
Hierarchical Softmax(分层softmax)
两种实现方法
1、CBOW
2、Skip-gram
Skip-gram
根据一个词,预测其上下文
CBOW(Continuous Bag-of-Words Model)
是一种根据上下文预测当前词语的出现概率的模型
似然函数:在上下文为Context(w)的情况下,预测w,当然是希望L越大越好,作为我们的训练目标
缺点:
(CBOW)输入层经过隐藏层最后softmax输出所有词的概率,然后反向传播梯度下降decrease loss。但这其中有一个很大的问题:在语料库很大的情况下,此方法从隐藏层到输出的softmax层的计算量很大,因为要计算所有词的softmax概率,再去找概率最大的值,
分层softmax思想:最优哈夫曼树
对于以上方法改缺点中,我们用最优哈夫曼树对其改进,优先预测出现频率较大的词的概率,从而减小计算量
哈夫曼树
哈夫曼树是一种带权路径长度最短的二叉树,也称最优二叉树
Hierarchical Softmax的设计思想:
在进行词预测的时候,由于我们的语料库中有成千上万个单词,进行softmax计算量是很大的,在我们生活中常用的词(高频)也就几百上千个,现构建哈夫曼树,将词出现的频率作为路径的权值,将出现频率高的词放在最前面,用二分类进行分层的判断,这样就能够重视常用的单词。
构造哈夫曼树过程:(分层、编码)
Logistic回归:判断走左子树还是右子树
以逻辑回归计算出的概率作为走左子树还是右子树(正负例)的概率
CBOW模型
-
输入层是上下文的词语的词向量,在训练CBOW模型,词
向量只是个副产品,确切来说,是CBOW模型的一个参数。
训练开始的时候,词向量是个随机值,随着训练的进行不
断被更新)。 -
投影层对其求和,所谓求和,就是简单的向量加法。
-
输出层输出最可能的词w。由于语料库中词汇量是固定的|C|
个,所以上述过程其实可以看做一个多分类问题。给定特
征,从|C|个分类中挑一个。
例子:
现设定一些参数
根据输入的 X 上下文,要预测结果为‘足球’出现的概率
设定向左为负例,向右为正例,根据‘足球’的编码(将频率高的词放在前面,编码时便突出了哈夫曼树的优势),计算出到达每个节点的概率,首先第一个应分为负类,第二个分为正类…直到达到我们的结果,负正正负,并将每一次的概率累乘即可得到结果。
CBOW求解目标
似然函数作为目标函数:在已知上下文context(w)的条件下,预测得到词w的概率最大
将根据编码得到的概率值计算进行合并:
*前面定义dj^w为对应节点的编码,当dj^w为为0时,用负例的概率,dj^w为为1时,用正例的概率
将P带入似然函数(目标函数)进行求解
*log a^2*b^3=2log a+3log b
梯度上升求解
(1)theata更新:按结果的编码更新参数
sigmoid函数的导数:
且log x求导等于自身,所以sigmoid的求导项只剩下1-sigmoid(x),带入偏导式得:
合并同类项
所以得到theate的更新表达式:
(2)对X的更新:初始是随机选择的词向量,需要对上下文Context(w)更新,上下文越准确,预测的词也越准确
对投影层的结果(为联系输入的大向量)进行更新:
由上面CBOW的模型介绍知道,Xw是上下文的词向量的和,并不是上下文单个词的词向量,word2vec采取的措施是直接将Xw的更新量整个应用到每个单词的词向量上去:(每个向量的更新都是跟合向量相关的,即上下文相互间是有联系的,让每个词按整体相同的趋势更新,能够保证得到类似的分布空间和逻辑)
*v(w)为单个词的向量
Negative Sampling 负采样模型
对于语料库非常大的模型来说,哈夫曼树表现的并不是很好,对于某些要预测的词,即使其频率很高,但仍被排在很多层之后,所以其编码可能很长,计算复杂度还是很高,负采样模型可以对其进行改进
负采样的核心思想:正常的上下文组合看成是1,不正常的上下文组合看成是0,那么问题转换为二分类问题
对于一个给定的正样本(Context(w) , w)我们希望最大化:
单个正负例:
对于整体希望每个正例都能预测正确:
Google提出的算法:
任何采样算法都应该保证词频越高的样本越容易被采样出来,如在负样本中,频率越高的词也越有可能成为负样本,根据词频将其公平的分配每个词语:
counter就是w的词频
于是我们将该线段公平的分配(词频越大,区间也越长):
*(由之前构建的较麻烦的哈夫曼树转变成了二分类问题)
接下来只要生成一个0-1之间的随机数(词频越大的越有可能随机到),看看落到哪个区间,就能采样到该区间的对应的单词了。
g(w)(目标函数):前面一项正例的概率,后面也为(1 - 负样本的概率=正样本的概率)正例的概率,对其进行累乘,也同样能通过似然函数的方式构造目标函数,使目标函数朝着正例的方向更新
*NEG(w)为负样本的空间
Negative Sampling的优化:
梯度上升:
参数theate的更新和词向量的更新: