3.2.2詞向量(Word2Vec)技術

詞袋法是以每個詞匯為特征,向量化表示一個文本;并且提供了幾種特征量化的技術,如CountVectorizer和TfidfVectorizer。詞袋法可以視作對文本向量化的表示技術,通過這項技術可以對文本之間在內容的相似性進行一定程序的度量。但是對于如下兩段文本,詞袋法技術似乎對計算他們的相似度表現(xiàn)的無能為力。
The cat is walking in the bedroom.
A dog was running across the kitchen.
盡管從語義上講,這兩段文本所描述的場景極為相似;但是,從詞袋法表示來看,這兩段文本唯一相同的詞匯是the,找不到任何語義層面的聯(lián)系。
而我們進一步學習到通過自然語言處理包,可以借助更加復雜的自然語言處理技術對文本進行分析。這使得我們不僅能夠對詞匯的具體詞性進行標注,甚至可以對句子進行解構。然而,即便我們能夠使用NLTK中的詞性標注技術對上述文本進行分析,找出對應詞匯在詞性方面的相似性,也無法針對具體詞匯之間的含義是否相似進行度量。
因此,為了尋找詞匯之間的相似度關系,我們視圖也將詞匯的表示向量化。
這樣就可以通過計算表示詞匯的向量之間的相似度,來度量詞匯之間的含義是否相似。而為了學習到這樣的詞向量表示,Yoshua教授等人Google研究員Mikolow等人分別從神經網(wǎng)絡模型的角度提出了自己的框架。

以輸入一句英文為例:The cat is walking in the bedroom。如果我們需要這句話中所有上下文為數(shù)量為4的連續(xù)詞匯片段,那么就有 The cat is walking、cat is walking in、is walking in the 以及 walking in the bedroom 這樣4個片段。從語言模型角度上來講,每個連續(xù)詞匯片段的最后一個單詞是什么,都是受前面三個詞匯制約。因此,這就形成了一個根據(jù)前面三個單詞,預測最后一個單詞的監(jiān)督學習系統(tǒng)。

如果用神經網(wǎng)絡框架來描述,上圖就代表一個監(jiān)督模型的神經網(wǎng)絡,當上下文數(shù)量為n的時候,這里的模型就是用前n-1個詞語,也就是w(t-1) … w(t-n+1),來預測第t個詞語w(t)。在神經網(wǎng)絡中,用于計算的都是這些詞的向量表示,如C(w(t-1)) 就是詞語 w(t-1) 的向量表示。

這里C(w(t-1))其實就是詞向量,但不是最終的詞向量,最終結果還需要多輪迭代計算。其實這些詞向量就是神經網(wǎng)絡里的參數(shù),生成詞向量的過程就是一個參數(shù)更新的過程。

注意:對于初學者來說這里有個坑,考慮一個問題:詞向量不是我們最終得到的嗎?那我們如何得到最初輸入的每個詞對應的詞向量C(w(t-1))、C(w(t-2))、、、C(w(t-n+1))?以下是我查閱資料后自己的理解:

在上圖中存在一個系數(shù)矩陣C(是一個NM的矩陣),其中N是詞典的長度,M是詞向量的維度。最底層的輸入其實是詞語的one-hot形式,one-hot也可以看成 1N的矩陣 ,與這個系數(shù)矩陣C(NM, M是word2vec詞向量維數(shù))相乘之后就可以得到1M的向量,這個向量就是這個詞對應的詞向量了。

從本質上來看,詞語w轉化為詞向量C(w),就是根據(jù)詞 w 的one-hot 形式,通過矩陣相乘,從系數(shù)矩陣C中取出一行。

還需注意的是,這個系數(shù)矩陣C,就是神經網(wǎng)絡的參數(shù),最初是隨機的,隨著訓練的進行不斷被更新。

用20類新聞文本進行詞向量訓練
from sklearn.datasets import fetch_20newsgroups
news=fetch_20newsgroups(subset='all')
X,y=news.data,news.target

from bs4 import BeautifulSoup
import nltk,re

#定義一個函數(shù)名為news_to_sentences講每條新聞中的句子逐一剝離出來,并返回一個句子的列表
def news_to_sentences(news):
    news_text=BeautifulSoup(news).get_text()
    tokenizer=nltk.data.load('tokenizers/punkt/english.pickle')
    raw_sentences=tokenizer.tokenize(news_text)
    sentences=[]
    for sent in raw_sentences:
        sentences.append(re.sub('[^a-zA-Z]',' ',sent.lower().strip()).split())
    return sentences
sentences=[]

示例:kaggle之電影評論文本情感分類

#將長篇新聞文本中的句子剝離出來,用于訓練
for x in X:
    sentences+=news_to_sentences(x)

from gensim.models import word2vec

#配置詞向量的維度
num_features=300
#保證被考慮的詞匯的頻度
min_word_count=20
#設定并行化訓練使用CPU計算核心的數(shù)量,多核可用
num_workers=2
#定義訓練詞向量的上下文窗口大小
context=5
downsampling=1e-3#1e-3第一個是數(shù)字1,不是字母l

from gensim.models import word2vec

#訓練詞向量模型
model=word2vec.Word2Vec(sentences,workers=num_workers,\
                       size=num_features,min_count=min_word_count,\
                       window=context,sample=downsampling)

#這個設定代表當前訓練好的詞向量為最終版,也可以加快模型的訓練速度
model.init_sims(replace=True)
#利用訓練好的模型,尋找訓練文本中與morning最相關的10個詞匯
model.most_similar('morning')

[('afternoon', 0.7969172596931458),
('weekend', 0.764119565486908),
('evening', 0.7500736117362976),
('saturday', 0.7279693484306335),
('night', 0.7039743661880493),
('friday', 0.6897615790367126),
('newspaper', 0.6688321828842163),
('summer', 0.6671631932258606),
('sunday', 0.6512582898139954),
('week', 0.6438664793968201)]

#利用訓練好的模型,尋找訓練文本中與email最相關的10個詞匯
model.most_similar('email')

[('mail', 0.7358647584915161),
('contact', 0.6991280913352966),
('mailed', 0.6708669066429138),
('replies', 0.6512271165847778),
('address', 0.630152702331543),
('send', 0.6236768364906311),
('archie', 0.6234195828437805),
('listserv', 0.6213445067405701),
('request', 0.6204395890235901),
('sas', 0.6121519804000854)]

結果表明,在不使用語言學詞典的前提下,詞向量技術仍然可以借助上下文信息找到詞匯之間的相似性。這一技術不僅大量專業(yè)人士的作業(yè)時間,而且也可以作為一個基礎模型應用到更加復雜的自然語言處理任務中。
最后需要指出的是,詞向量的訓練結果很大程度上受所提供的文本影響。換言之,這些詞向量絕不是固定的;您可以靈活運用這個模型,訓練不同文本內部獨有的詞向量。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

友情鏈接更多精彩內容