自然语言处理——N-gram模型

NLP相关知识理解整理


一、N-gram模型简介

N-gram模型属于概率语言模型,其要解决的问题其实很简单,那就是从是否符合自然语言的角度评估一个句子的质量。在这个问题中,句子 W W W被建模成词的排列 W = w 1 , w 2 , . . . w n W=w_1,w_2,...w_n W=w1,w2,...wn,所谓质量就就是句子出现的概率,也即该排列出现的联合概率:

P ( W ) = P ( w 1 , w 2 , . . . w n ) = P ( w 1 ) P ( w 2 ∣ w 1 ) . . . P ( w n ∣ w 1 , w 2 . . . w n − 1 ) P(W)=P(w_1,w_2,...w_n)=P(w_1)P(w_2|w_1)...P(w_n|w_1,w_2...w_{n-1}) P(W)=P(w1,w2,...wn)=P(w1)P(w2w1)...P(wnw1,w2...wn1)

但是要计算概率要么通过概率密度函数,要么用统计概率近似。自然语言的概率密度函数我们肯定是无法知道了,那么就要用统计概率,所以必须要有一个自然语言的样本库,里面包含了大量的自然语言的句子实例,在N-gram模型中用到的便是语料库

那么怎么通过语料库来计算句子出现的概率呢?这就涉及到马尔科夫链的假设,即当前词出现的概率 P ( w i ) P(w_i) P(wi)仅与前N-1个词有关,这里的N就对应N-gram里面的N。所以N-gram模型的构建只需要计算出所有的N以内的条件概率即可:

P ( w i ) , P ( w i ∣ w i − 1 ) . . . . P ( w i ∣ w i − n + 1 ) P(w_i),P(w_i|w_{i-1})....P(w_i|w_{i-n+1}) P(wi),P(wiwi1)....P(wiwin+1)

例如常用的当N=3时,句子W出现概率就简化为:

P ( W ) = P ( w 1 , w 2 , . . . w n ) = P ( w 1 ) P ( w 2 ∣ w 1 ) P ( w 3 ∣ w 1 , w 2 ) . . . P ( w n ∣ w n − 2 , w n − 1 ) P(W)=P(w_1,w_2,...w_n)=P(w_1)P(w_2|w_1)P(w_3|w_1,w_2)...P(w_n|w_{n-2},w_{n-1}) P(W)=P(w1,w2,...wn)=P(w1)P(w2w1)P(w3w1,w2)...P(wnwn2,wn1)

可以看到当N增大时,需要计算的概率将会大大增多,其计算量几乎是与N成指数关系的增长(因为每多考虑一阶,每个词都大约需要多考虑M个“新的概率”)。谷歌当初使用的N=4的语言模型需要500台以上的服务器进行存储,这是不可想象的。

而且即使N取的再大,也无法完全覆盖后文对前文的依赖关系,语言的上下文联系可以跨度很大,而N的增长对计算量增大带来的压力完全无法满足这种大跨度的上下文联系。

二、N-gram模型的问题与思考

1.数据稀疏

首先最容易出现的问题就是数据稀疏的问题,有些词或者词组在语料库中可能出现的很少甚至没有出现过,这就会导致该低频词或词组计算概率时得到非常小的概率,从而导致估计不可靠。

解决数据稀疏最直接的想法是增大语料库的规模,但是其问题也很明显,增加的语料库中占主体的仍然是高频词。

另一种方法是平滑,这种方法通过优化概率的计算,提高低频词的概率。其主要思想是对不可靠的统计概率(出现次数较少的词)打折扣,然后将这些概率分配给未出现的词。例如拉普拉斯平滑通过对所有的词、词组进行加一来进行平滑。然而平滑也存在问题,以拉普拉斯平滑为例,假设语料库规模为M(总的词数),词表大小为V(出现不同词的个数),考虑一个只出现一次的词w的概率:

P ( w ) = 1 M P(w)=\frac {1}{M} P(w)=M1

加入平滑后:

P ( w ) = 2 M + V P(w)=\frac{2}{M+V} P(w)=M+V2

我们知道语料库的规模是远大于词表大小的,所以w的概率经过平滑之后几乎提高了一倍!那么大量低频词经过平滑后将会提高不少概率,这对概率分布的影响比想象中要大得多。

还有一种避免数据稀疏的方法是回退,当计算到词组的概率为零时,便回退到低一阶的条件概率来代替,如果还为零则继续回退,k是一个可调参数。

P ( w 3 ∣ w 1 , w 2 ) = k P ( w 3 ∣ w 2 ) , i f P ( w 3 ∣ w 1 , w 2 ) = 0 P(w_3|w_1,w_2)=kP(w_3|w_2),if P(w_3|w_1,w_2)=0 P(w3w1,w2)=kP(w3w2),ifP(w3w1,w2)=0

2.思考总结

N-gram模型其实就是基于最朴素的现在与历史相关的思想,来进行词句的评估,具备良好的可解释性,虽然现在看来它过于简单了,但是当时贾里尼克通过它很好地解决了语音识别的问题,把识别准确率从70%一下子提高到了90%。而且这种基于统计概率来处理自然语言的方法也撼动了基于语法规则的传统方法的地位,甚至改变自然语言处理的研究方法。
但是其不足也很明显,除了数据稀疏这个模型本身存在的问题,N-gram模型的假设也是有问题的。首先,只考虑单向的相关性显然会丢失掉部分信,基于N-gram模型进行空缺词的填补的话,其总是会倾向于更高出现率的词,且对后续词与缺失词的相关性无法进行利用。
其次,仅从概率的角度,不考虑词本身的相似性,将会丢失更多的语义信息,例如近义词的概率可能会相去甚远。

  • 2
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
n-gram模型是一种用于自然语言处理的统计语言模型,用于预测一个词语在给定前文的情况下出现的概率。在R语言中,可以使用`quanteda`包来实现n-gram模型。 首先,需要安装`quanteda`包,可以使用以下命令进行安装: ```R install.packages("quanteda") ``` 安装完成后,可以使用以下代码创建n-gram模型: ```R library(quanteda) # 创建一个文本对象 text <- c("I love coding in R", "R is a powerful language") # 创建一个corpus对象 corpus <- corpus(text) # 创建一个token对象 tokens <- tokens(corpus) # 创建一个n-gram模型 ngram_model <- tokens_ngrams(tokens, n = 2) ``` 上述代码中,我们首先创建了一个文本对象`text`,然后将其转换为corpus对象`corpus`,再将corpus对象转换为token对象`tokens`。最后,使用`tokens_ngrams`函数创建了一个n-gram模型`ngram_model`,其中`n`参数指定了n-gram的大小。 创建完n-gram模型后,可以使用以下代码获取n-gram的频率信息: ```R # 获取n-gram的频率信息 ngram_freq <- textstat_frequency(ngram_model) ``` 上述代码中,我们使用`textstat_frequency`函数获取了n-gram模型中各个n-gram的频率信息。 除了获取频率信息外,还可以使用n-gram模型进行文本生成和预测。例如,可以使用以下代码生成一个新的文本: ```R # 使用n-gram模型生成新的文本 new_text <- generate(ngram_model, n = 10) ``` 上述代码中,我们使用`generate`函数根据n-gram模型生成了一个包含10个词语的新文本。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值