如何计算给定一个unigram语言模型_n-gram语言模型原理到实践
最近開(kāi)始復(fù)習(xí)一些nlp基礎(chǔ)知識(shí),今天來(lái)回顧一下自然語(yǔ)言處理的重要技術(shù)語(yǔ)言模型(language model)。
1 什么是語(yǔ)言模型
語(yǔ)言模型就是衡量一句話(huà)概率的模型,可以用來(lái)判斷這句話(huà)為人話(huà)的概率。我們可以把一段自然語(yǔ)言文本看作一段離散的時(shí)間序列。假設(shè)一段長(zhǎng)度為T(mén)的文本中的詞依次為
,那么在離散的時(shí)間序列中, 可看作在時(shí)間步(time step) 的輸出或標(biāo)簽。給定一個(gè)長(zhǎng)度為T(mén)的詞的序列 ,語(yǔ)言模型將計(jì)算該序列的概率:語(yǔ)言模型可用于提升語(yǔ)音識(shí)別和機(jī)器翻譯的性能。例如,在語(yǔ)音識(shí)別中,給定一段“廚房里食油用完了”的語(yǔ)音,有可能會(huì)輸出“廚房里食油用完了”和“廚房里石油用完了”這兩個(gè)讀音完全一樣的文本序列。如果語(yǔ)言模型判斷出前者的概率大于后者的概率,我們就可以根據(jù)相同讀音的語(yǔ)音輸出“廚房里食油用完了”的文本序列。在機(jī)器翻譯中,如果對(duì)英文“you go first”逐詞翻譯成中文的話(huà),可能得到“你走先”“你先走”等排列方式的文本序列。如果語(yǔ)言模型判斷出“你先走”的概率大于其他排列方式的文本序列的概率,我們就可以把“you go first”翻譯成"你先走"。(摘自《動(dòng)手學(xué)深度學(xué)習(xí)》)
2 語(yǔ)言模型的計(jì)算
既然語(yǔ)言模型很有用,那么我們?cè)撊绾斡?jì)算呢?假設(shè)一段含有4個(gè)詞的文本序列w1,w2,w3,w4,則該序列的概率為
一般的,對(duì)于序列
我們有其中,條件概率
當(dāng)序列非常長(zhǎng)的時(shí)候,計(jì)算和存儲(chǔ)多個(gè)詞共同出現(xiàn)的概率的復(fù)雜度會(huì)呈指數(shù)級(jí)別增長(zhǎng)。而且數(shù)據(jù)稀疏十分嚴(yán)重,沒(méi)有足夠大的預(yù)料能夠滿(mǎn)足多個(gè)詞的共現(xiàn),即不滿(mǎn)足大數(shù)定律而導(dǎo)致概率失真。并且由Zipf定律(Zipf's Law)知道在自然語(yǔ)言中大部分詞都是低頻詞,很難通過(guò)增加數(shù)據(jù)集來(lái)避免數(shù)據(jù)稀疏問(wèn)題。因此多個(gè)詞共同出現(xiàn)的次數(shù)在語(yǔ)料庫(kù)中可能為0,導(dǎo)致序列概率直接為0。
3 從聯(lián)合概率鏈到n-gram語(yǔ)言模型
上面我們已經(jīng)討論了語(yǔ)言模型的聯(lián)合概率計(jì)算是很困難的,如何簡(jiǎn)化語(yǔ)言模型的計(jì)算呢?這里便引入了馬爾可夫假設(shè):一個(gè)詞的出現(xiàn)只與前面n個(gè)詞相關(guān),即n階馬爾可夫鏈。
如果n=1,那么有
。當(dāng)n=1,n=2,n=3時(shí),我們將其分別稱(chēng)作一元語(yǔ)法(unigram)、二元語(yǔ)法(bigram)和三元語(yǔ)法(trigram)。
對(duì)于unigram來(lái)說(shuō),滿(mǎn)足了獨(dú)立性假設(shè),馬爾可夫假設(shè)可以看做在獨(dú)立性假設(shè)的基礎(chǔ)上加上了條件依賴(lài)。
例如,長(zhǎng)度為4的序列
在一元語(yǔ)法、二元語(yǔ)法和三元語(yǔ)法中的概率分別為嚴(yán)格來(lái)說(shuō),對(duì)于2-gram和3-gram來(lái)說(shuō),這樣計(jì)算的概率有偏差,對(duì)于2-gram,w1也應(yīng)該計(jì)算條件概率,這時(shí)需要給句子加上起始和結(jié)束位標(biāo)志。下面舉個(gè)例子計(jì)算2-gram。
<s>I am Sam</s>
<s>Sam I am</s>
<s>I do not like green eggs and ham</s>
...
因此
("I am Sam") = ("Sam I am") = ("I am Sam") > ("Sam I am") 可以知道“I am Sam”要比“Sam I am”通順。但是在實(shí)際情況下,如果要嚴(yán)格計(jì)算語(yǔ)言模型,需要對(duì)語(yǔ)料進(jìn)行分句,然后在句首和句尾添加起始符和結(jié)束符,這樣比較麻煩。所以在很多情況下我們會(huì)使用上面說(shuō)的計(jì)算方法來(lái)近似,可能也是因?yàn)檫@個(gè)原因我們很少看見(jiàn)加起始符和結(jié)束符的計(jì)算操作,只要句子計(jì)算的標(biāo)準(zhǔn)保持一致,還是能夠準(zhǔn)確判斷概率大小的。(我的觀點(diǎn),不一定準(zhǔn)確,如果有不對(duì)的地方歡迎指正~)
4 平滑技術(shù)
為了解決零概率問(wèn)題呢,我們需要給“未出現(xiàn)的n-gram條件概率分布一個(gè)非零估計(jì)值,相應(yīng)得需要降低已出現(xiàn)n-gram條件概率分布,且經(jīng)數(shù)據(jù)平滑后一定保證概率和為1”。這就是平滑技術(shù)的基本思想。
4.1 拉普拉斯平滑
這是最古老的一種平滑方法,又稱(chēng)加一平滑法,其保證每個(gè)n-gram在訓(xùn)練語(yǔ)料中至少出現(xiàn)1次。以計(jì)算概率 P(“優(yōu)惠”|“發(fā)票”,“點(diǎn)數(shù)”)為例,公式如下:
在所有不重復(fù)的三元組的個(gè)數(shù)遠(yuǎn)大于(“發(fā)票”,“點(diǎn)數(shù)”)出現(xiàn)的次數(shù)時(shí),即訓(xùn)練語(yǔ)料庫(kù)中絕大部分n-gram都是未出現(xiàn)的情況(一般都是如此),拉普拉斯平滑有“喧賓奪主”的現(xiàn)象,效果不佳。
4.2 古德圖靈(Good Turing)平滑
通過(guò)對(duì)語(yǔ)料庫(kù)的統(tǒng)計(jì),我們能夠知道出現(xiàn)r次(r>0)的n元組的個(gè)數(shù)為
。可以令從未出現(xiàn)的n元組的個(gè)數(shù)為 。古德圖靈平滑的思想是:- 出現(xiàn)0次的n元組也不能認(rèn)為其是0次,應(yīng)該給它一個(gè)比較小的估計(jì)值,比如為 次。
- 為了保證總共的(出現(xiàn)和未出現(xiàn)的)n元組的次數(shù)不變,其他所有已出現(xiàn)的n元組的次數(shù)r應(yīng)該打一個(gè)折扣,比如為 次。
- 然后再用新的 去計(jì)算各個(gè)條件概率。
所以問(wèn)題的關(guān)鍵是計(jì)算
。為了保證平滑前后n元組的總共出現(xiàn)次數(shù)不變,有:所以干脆令:
一般來(lái)說(shuō),出現(xiàn)一次的詞的數(shù)量比出現(xiàn)兩次的多,出現(xiàn)兩次的比三次的多。這種規(guī)律稱(chēng)為Zipf定律(Zipf’s Law)。下圖是一個(gè)小語(yǔ)料上出現(xiàn)r次的詞的數(shù)量
和r的關(guān)系。可以看出r越大,詞的數(shù)量
越小,即 。因此,一般情況下 ,而 。這樣就給未出現(xiàn)的詞賦予了一個(gè)很小的非零值,從而解決了零概率的問(wèn)題。同時(shí)下調(diào)了出現(xiàn)概率很低的詞的概率。當(dāng)然,在實(shí)際的自然語(yǔ)言處理中,一般會(huì)設(shè)置一個(gè)閾值T(一般取8~10),僅對(duì)出現(xiàn)次數(shù)小于T的詞做上述平滑。并且,因?yàn)閷?shí)際語(yǔ)料的統(tǒng)計(jì)情況使得
不一定成立, 情況也可能出現(xiàn),所以需要使用曲線(xiàn)擬合的方式替換掉原有的 ,并使用如下Kartz退避公式計(jì)算 :4.3 組合估計(jì)平滑
不管是拉普拉斯平滑,還是古德圖靈平滑技術(shù),對(duì)于未出現(xiàn)的n元組都一視同仁,而這難免存在不合理。 因?yàn)槟呐率俏窗l(fā)生的事件,相互之間真實(shí)的概率也會(huì)存在差別。
另一方面,一個(gè)n元組可能未出現(xiàn),但是其(n-1)元組或者(n-2)元組是出現(xiàn)過(guò)的,這些信息如果不利用就直接浪費(fèi)掉了。在沒(méi)有足夠的數(shù)據(jù)對(duì)高元n-gram模型進(jìn)行概率估計(jì)時(shí),低元n-gram模型通常可以提供有用的信息。因此可以利用利用低元n-gram模型的信息對(duì)高元n-gram模型進(jìn)行估計(jì):
- 如果低元n-gram模型的概率本來(lái)就很低,那么就給高元n-gram模型一個(gè)較低的估計(jì)值;
- 如果低元n-gram模型有一個(gè)中等的概率,那么就給高元n-gram模型一個(gè)較高的估計(jì)值。
常用的組合估計(jì)算法有線(xiàn)性差值法和Katz回退法。具體公式比較復(fù)雜,這里就不列了。感興趣的同學(xué)可參考 Christopher D. Manning 的《統(tǒng)計(jì)自然語(yǔ)言處理基礎(chǔ)》
5 動(dòng)手實(shí)現(xiàn)n-gram語(yǔ)言模型(bigram為例)
import pandas as pd import re import jieba from collections import Counteroriginal_data = pd.read_csv('./data/sqlResult_1558435.csv', encoding='gb18030') articles = original_data['content'].tolist()# 去除標(biāo)點(diǎn)符號(hào)、英文字符、數(shù)字 def clean(article):clean_article = ''.join(re.findall('w+', str(article))) # 去除標(biāo)點(diǎn)符號(hào)pattern = re.compile('[A-Za-zd]+')clean_article = pattern.sub('', str(clean_article)) # 去除英文字符和數(shù)字return clean_article# 將清洗后的文本保存到文件中 def save(articles):with open('./data/article_9k.txt', 'w', encoding='utf-8') as f:for a in articles:f.write(a + 'n')clean_articles = [clean(article) for article in articles] save(clean_articles)# 分詞處理 def cut_text():words_list = []with open('./data/article_9k.txt', 'r') as f:count = 0for line in f:words = list(jieba.cut(line.strip('n')))words_list += wordsreturn words_listwords_list = cut_text() words_count = Counter(words_list) TOKENS_2GRAM = [''.join(words_list[i:i+2]) for i in range(len(words_list)-1)] words_count2 = Counter(TOKENS_2GRAM)words_list_len = len(words_list) unique_words_len = len(words_count) unique_bigram_len = len(words_count2)# 計(jì)算詞獨(dú)立出現(xiàn)的概率,采用拉普拉斯平滑 def prob_1(word):return (words_count[word] + 1) / (words_list_len + unique_words_len)# 計(jì)算條件概率,采用拉普拉斯平滑 def prob_2(word1, word2):return (words_count2[word1+word2] + 1) / (words_count[word1] + unique_bigram_len)# 構(gòu)建2-gram語(yǔ)言模型 def bigram_model(sentence):words = list(jieba.cut(sentence))probility = prob_1(words[0])for index in range(len(words)-1):probility *= prob_2(words[index], words[index+1])return probilitysent1 = "我愛(ài)你" sent2 = "我你愛(ài)" sent3 = "今天天氣真好" sent4 = "今天真天氣好" sent5 = "你先走" sent6 = "你走先" print(bigram_model(sent1)) print(bigram_model(sent2)) print(bigram_model(sent3)) print(bigram_model(sent4)) print(bigram_model(sent5)) print(bigram_model(sent6))輸出:
5.9607783295715594e-06
1.2585314454141385e-14
6.751764045254859e-19
6.959695538300923e-24
1.2520998402585423e-15
3.909475699071306e-16
總結(jié)
以上是生活随笔為你收集整理的如何计算给定一个unigram语言模型_n-gram语言模型原理到实践的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: kdj超卖_一个判断股票超买超卖现象的指
- 下一篇: 部署环境_Jenkins环境搭建和部署项