本文主要內(nèi)容翻譯自 Word2vec Tutorial
Gemsim 安裝
快速安裝
easy install -U gensim
pip install --upgrade gensim
依賴
Python >= 2.6
NumPy >= 1.3
SciPy >= 0.7
輸入
Gensim Word2vec 使用一個句子序列作為其輸入初坠,每個句子包含一個單詞列表甘畅。
sentences = [['first', 'sentence'], ['second', 'sentence']]
# train word2vec on the two sentences
model = gensim.models.Word2Vec(sentences, min_count=1)
用 Python 內(nèi)置的 list 類型作為輸入很方便,但當輸入內(nèi)容較多時,會占用很大的內(nèi)存空間端幼。Gemsim 的輸入只要求序列化的句子,而不需要將所有輸入都存儲在內(nèi)存中弧满。簡單來說婆跑,可以輸入一個句子,處理它庭呜,刪除它滑进,再載入另外一個句子。
舉例來說募谎, 假如輸入分散在硬盤的多個文件中扶关,每個句子一行,那么不需要將所有輸入先行存儲在內(nèi)存中数冬,Word2vec 可以一個文件一個文件节槐,一行一行地進行處理。
class MySentences(object):
def __init__(self, dirname):
self.dirname = dirname
def __iter__(self):
for fname in os.listdir(self.dirname):
for line in open(os.path.join(self.dirname, fname)):
yield line.split()
sentences = MySentences('/some/directory') # a memory-friendly iterator
model = gensim.models.Word2Vec(sentences)
如果希望對文件中的內(nèi)容進行預(yù)處理拐纱,舉例來說铜异,轉(zhuǎn)換編碼,大小寫轉(zhuǎn)換秸架,去除數(shù)字等操作揍庄,均可以在 MySentences
迭代器中完成,完全獨立于 Word2vec东抹。Word2vec 只負責(zé)接收 yield 的輸入蚂子。
針對高級用戶:調(diào)用 Word2Vec(sentences, iter=1)
會調(diào)用句子迭代器運行兩次(一般來說沃测,會運行 iter+1
次,默認情況下 iter=5
)食茎。第一次運行負責(zé)收集單詞和它們的出現(xiàn)頻率芽突,從而構(gòu)造一個內(nèi)部字典樹。第二次以及以后的運行負責(zé)訓(xùn)練神經(jīng)模型董瞻。這兩次運行(iter+1
)也可以被手動初始化寞蚌,如果輸入流是無法重復(fù)利用的,也可以用下面的方式對其進行初始化钠糊。
model = gensim.models.Word2Vec(iter=1) # an empty model, no training yet
model.build_vocab(some_sentences) # can be a non-repeatable, 1-pass generator
model.train(other_sentences) # can be a non-repeatable, 1-pass generator
如果對 Python 中迭代器挟秤,可迭代的,生成器這些概念不是很理解抄伍,可以參考下文艘刚。
Python關(guān)鍵字yield的解釋
訓(xùn)練
Word2vec 有多個影響訓(xùn)練速度和質(zhì)量的參數(shù)。
其中之一是用來修剪內(nèi)部字典樹的截珍。在一個數(shù)以億計的預(yù)料中出現(xiàn)一到兩次的單詞非常有可能是噪音或不需要被關(guān)注的攀甚。另外,也沒有足夠的數(shù)據(jù)對他們進行有意義的訓(xùn)練岗喉。因此秋度,最好的辦法就是直接將他們忽略掉。
model = Word2Vec(sentences, min_count=10) # default value is 5
對于設(shè)定 min_count
的值钱床,合理的范圍是0 - 100荚斯,可以根據(jù)數(shù)據(jù)集的規(guī)模進行調(diào)整。
另一個參數(shù)是神經(jīng)網(wǎng)絡(luò) NN 層單元數(shù)查牌,它也對應(yīng)了訓(xùn)練算法的自由程度事期。
model = Word2Vec(sentences, size=200) # default value is 100
更大的 size
值需要更多的訓(xùn)練數(shù)據(jù),但也同時可以得到更準確的模型纸颜。合理的取值范圍是幾十到幾百兽泣。
最后一個主要參數(shù)是訓(xùn)練并行粒度,用來加速訓(xùn)練胁孙。
model = Word2Vec(sentences, workers=4) # default = 1 worker = no parallelization
該參數(shù)只有在機器已安裝 Cython 情況下才會起到作用唠倦。如沒有 Cython,則只能單核運行浊洞。
內(nèi)存
在內(nèi)部牵敷,Word2vec 模型的參數(shù)以矩陣形式存儲(NumPy 數(shù)組),數(shù)組的大小為 #vocabulary 乘以 #size 的浮點數(shù) (4 bytes)法希。
三個如上的矩陣被存儲在內(nèi)存中(將其簡化為兩個或一個的工作進行中)枷餐。如果輸入中存在 100,000 個互異的詞,神經(jīng)網(wǎng)絡(luò)規(guī)模 size
設(shè)為200苫亦,則該模型大致需要內(nèi)存
100,000 * 200 * 3 * 4 bytes = ~229MB
毛肋。
除此之外怨咪,還需要一些額外的空間存儲字典樹,但除非輸入內(nèi)容極端長润匙,內(nèi)存主要仍被上文所提到的矩陣所占用诗眨。
評估
Word2vec 訓(xùn)練是一個非監(jiān)督任務(wù),很難客觀地評估結(jié)果孕讳。評估要依賴于后續(xù)的實際應(yīng)用場景匠楚。Google 公布了一個包含 20,000 語法語義的測試樣例,形式為 “A is to B as C is to D”厂财。
需要注意的是芋簿,如在此測試樣例上展示良好性能并不意味著在其它應(yīng)用場景依然有效,反之亦然璃饱。
存儲和載入模型
使用 Gensim 的方法進行存儲和載入模型
model.save('/tmp/mymodel')
new_model = gensim.models.Word2Vec.load('/tmp/mymodel')
該方法將模型內(nèi)部的 NumPy 矩陣從硬盤載入到虛擬內(nèi)存与斤。另外,可以使用如下的方法載入原生 C 工具生成的模型荚恶,文本和二進制形式的均可撩穿。
model = Word2Vec.load_word2vec_format('/tmp/vectors.txt', binary=False)
# using gzipped/bz2 input works too, no need to unzip:
model = Word2Vec.load_word2vec_format('/tmp/vectors.bin.gz', binary=True)
在線訓(xùn)練和恢復(fù)訓(xùn)練
高級用戶可以載入模型后用更多的預(yù)料對其進行訓(xùn)練,你可能要對參數(shù) total_words
進行調(diào)整谒撼,取決于希望達到的學(xué)習(xí)率食寡。
model = gensim.models.Word2Vec.load('/tmp/mymodel')
model.train(more_sentences)
從原生 C 工具生成的模型載入后無法繼續(xù)進行訓(xùn)練,仍然可以對該模型進行查詢和相關(guān)度計算操作嗤栓,但由于字典樹的丟失冻河,無法繼續(xù)進行訓(xùn)練。
使用模型
Word2vec 支持以下多種詞語相似度任務(wù):
model.most_similar(positive=['woman', 'king'], negative=['man'], topn=1)
[('queen', 0.50882536)]
model.doesnt_match("breakfast cereal dinner lunch";.split())
'cereal'
model.similarity('woman', 'man')
0.73723527
可以用如下方法查詢詞向量:
model['computer'] # raw NumPy vector of a word
array([-0.00449447, -0.00310097, 0.02421786, ...], dtype=float32)
如需要全體的詞向量茉帅,可以調(diào)用 model.syn0
返回一個 2D 的 NumPy 矩陣。