1.什么是word2vector?
我們先來看一個問題,假如有一個句子 " the dog bark at the mailman"。
假如用向量來表示每個單詞,我們最先想到的是用one hot 編碼的方式來表達每個單詞,具體來說。
the 可以表示為 [1,0,0,0,0]
dog 可以表示為 [0,1,0,0,0]
bark 可以表示為 [0,0,1,0,0]
at 可以表示為[0,0,0,1,0]
mailman可以表示為[0,0,0,0,1]
我們可以看到每個單詞其實就用一個向量來表示。我們發現幾個問題:
第一,每個向量之間相互正交的(內積為0)。也就是說詞與詞之間是沒有任何關系的。
第二,每個詞的向量維度和不同詞的個數有關。比方說,在上面的這個句子里,有5個不同的詞,所以向量的維度是5。然而往往現實中,一篇文章的中不同的詞的個數是很多的。這樣,向量的維度會非常的高。
這種對詞的向量表示方法存在着以上的問題,忽略了詞與詞之間的關系(比如說,dog和cat都是動物,並非完全無關系)。維度太高的向量作為模型輸入會導致模型變的復雜(模型復雜需要更多的訓練樣本才能夠收斂)
那么是否存在一種更加合理的對詞的用向量的表達方式呢?有的,其實就是word embedding。
word embedding說的簡單一點其實就是將高維稀疏的向量降維成稠密的低維向量。(一種高維到低維的映射)
那么如和實現word embedding?
w2v其實就是一種高效實現word embedding的工具。
所以,如果用一句話來描述word2vector的話你會怎么描述?簡單的說,我覺得可以這么說w2v其實是一種將單詞轉化向量的工具。這一種向量的其實是對單詞更有效的表達。
2.word2vector怎么做?
上面提到為了得到表達能力更強的詞向量,我們可以進行word embedding。那么w2v是如何實現word embedding的呢?
下面我總結一下主要的思想,詳細的原理可以參考以上給的三篇文章。
2.1 Skip-Gram& CBOW
在介紹w2v模型之前,先介紹兩個模型。一個是Skip-Gram和CBOW(Continuous Bag-of-Words)。
首先看CBOW,它的做法是,將一個詞所在的上下文中的詞作為輸入,而那個詞本身作為輸出。

再來看Skip-Gram,它的做法和CBOW相反,將一個詞所在的上下文中的詞作為輸出,而詞本身作為輸入。(下面有例子說明)

另外,我們介紹這兩個模型都會涉及到的一個重要參數。
window_size:窗口大小。
舉一個例子,還是上面那句話:" the dog bark at the mailman"
假設window_size取1時,利用CBOW模型可以得到:
([the,bark],dog)
([dog,at],bark)
([bark,the],at)
([at,mailman],the)
一共4組數據。
同樣滴,假設window_size還是1,利用Skip-Gram模型可以得到:
(dog,[the,bark])
(bark,[dog,at])
(at,[bark,the])
(the,[at,mailman])
對於每組數據會稍微做一下處理。
比如對於第一組 (dog,[the,bark])一般處理成
(dog,the),(dog,bark)。類似有:
(bark,dog),(bark,at),(at,bark),(at,the),(the,at),(the,mailman)共8組數據。
2.2 word2vector
下面就可以直接介紹如何進行w2v,上面提到w2v可以看作是一個將高維空間映射到低維空間的過程,用一個單層神經網絡就可以實現這種功能(和自編碼器有點類似其實)。
對於CBOW,假如還是上面的句子,訓練數據是([the,brak],dog)那么網絡的輸入輸出如下圖所示:

這里有幾個細節:
1.上面介紹CBOW模型的時有一個模型的結構圖,其中的SUM意思其實就是把各個上下文的詞one-hot后的向量相加。
比如對於the的向量是[1,0,0,0,0]。bark向量是[0,0,1,0,0],SUM之后就是[1,0,1,0,0]這就是網絡的輸入。
輸出就是[0,1,0,0,0]-dog
2.我們所謂的embedding vetcor其實就第二個紅框里的線,每一根線其實就是一個權值。
3.第二個框里的紅線其實就是dog這個單詞的embedding結果(由5維變成3維)
4.這個單層NN訓練完畢之后有用的部分就是embedding martrix這部分,其大小為 輸入個數(詞匯表長度)×embedding后的維度。
類似對於Skip-Gram模型有:

當取訓練數據(dog,bark)時,網絡結構如上圖,對比上面的CBOW最大的不同其實就是在於輸入數據。
2.3 其他問題
上面只是關於w2v一個非常淺顯方面的介紹,其實還有比如 負采樣(negative sampling),層級SoftMax以及代碼解讀等,自己嘗試寫了幾次,但是感覺都並沒有太多的新東西,也沒有什么犀利的見解。所以就沒貼上來,下面只是簡單概括一下負采樣。
1.為什么需要負采樣?
其實理由很簡單,比如對於CBOW模型,已經知道詞w的上下文Context(w)。如果希望預測詞w,因此,當給定Context(w)時,詞w就是一個正樣本,其他詞就是負樣本。在上面的網絡里面我們可以容易地看出輸出有多少個就是詞匯表里有多少個詞。通常來說,我們的詞匯表是非常龐大的,對於某一個詞w,每個負樣本逐個去算一次計算的代價是很大的。
-------------------------------------------------------------------------------------------------------------------------------------------------------------
網上已經有許多對w2v的介紹了,這里只是做一個簡單的概括。下面這篇文章我認為是關於W2V寫的比較好的文章:
另外一篇是關於Skip-Gram和CBow的介紹。
邏輯比較清晰的綜述文章:
數學原理很清晰很短的一篇文章(也有關於負采樣的簡單說明)
---------------------------------------------------------------------------------------------------------------------------------------------------------------
僅為學習記錄之用,侵刪。
參考:https://blog.csdn.net/qq_22238533/article/details/78534743
https://www.leiphone.com/news/201706/PamWKpfRFEI42McI.html