詞幹提取(stemming)與詞形還原(lemmatization)
在英語中,一個單詞常常是另一個單詞的“變種”,如:happy=>happiness,這裡happy叫做happiness的詞幹(stem)。在資訊檢索系統中,我們常常做的一件事,就是在Term規範化過程中,提取詞幹(stemming),即除去英文單詞分詞變換形式的結尾。
應用最為廣泛的、中等複雜程度的、基於字尾剝離的詞幹提取演算法是波特詞幹演算法,也叫波特詞幹器(Porter Stemmer)。詳見官方網站。比較熱門的檢索系統包括Lucene、Whoosh等中的詞幹過濾器就是採用的波特詞幹演算法。
簡單說一下歷史:
馬丁.波特博士(Dr. Martin Porter)於1979年,在英國劍橋大學,計算機實驗室,發明了波特詞幹演算法。
波特詞幹演算法當時是作為一個大型IR專案的一部分被提出的。它的原始論文為:
C.J. van Rijsbergen, S.E. Robertson and M.F. Porter, 1980. New models in probabilistic information retrieval. London: British Library. (British Library Research and Development Report, no. 5587).
最初的波特詞幹提取演算法是使用BCPL語言編寫的。作者在其網站上公佈了各種語言的實現版本,其中C語言的版本是作者編寫的最權威的版本。
波特詞幹器適用於涉及到提取詞幹的IR研究工作,其實驗結果是可重複的,言外之意是說,波特詞幹器的輸出結果是確定性的,不是隨機的。(還有基於隨機的高階詞幹提取演算法,雖然會更準確,但同時也更加複雜)。
詞幹提取演算法無法達到100%的準確程度,因為語言單詞本身的變化存在著許多例外的情況,無法概括到一般的規則中。使用詞幹提取演算法能夠幫助提高IR的效能。
波特詞幹演算法的官方網站上,有各個語言的實現版本(其實都是C標準的各個翻譯形式)。各位要應用到實際生產中可以直接下載對應的版本。本文將會分析Java語言的原始碼。在今後的文章中,再介紹使用Python特性優化過的版本。(Python原版幾乎就是C語言版本的翻譯,這也就意味著不能充分利用Python的語言特性。)
在實際處理中,需要分六步走。首先,我們先定義一個Stemmer類。
?1 2 3 4 5 6 7 8 9 10 11 12 13 |
class Stemmer
{ private char []
b;
private int
i, /*
b中的元素位置(偏移量) */
i_end,
/* 要抽取詞幹單詞的結束位置 */
j,
k;
private
static final int INC = 50;
/*
隨著b的大小增加陣列要增長的長度(防止溢位) */
public Stemmer()
{
b = new char [INC];
i
= 0 ;
i_end
= 0 ;
}
}
|
這裡,b是一個數組,用來存待詞幹提取的單詞(以char的形式)。這裡的變數k會隨著詞幹抽取而變化。
接著,我們要新增單詞來進行處理:
?1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
/** <
|