??在目前的自然語言處理、數據挖掘以及機器學習中,相似性度量算法是一種比較常用的算法,是文本計算的基礎。相似性度量有助于幫助開發者發現數據關聯性,其核心點在于兩個方面:1.數據的特征表示。2. 集合之間的表示方法。
1. Jaccard相似系數
??Jaccard index, 又稱為Jaccard相似系數(Jaccard similarity coefficient),也稱之為雅可比相似度系數,用于比較有限樣本集之間的相似性與差異性。Jaccard系數值越大,樣本相似度越高。
狹義的Jaccard相似系數
??狹義的Jaccard相似系數是通過兩組樣本直接的交集與總集之間的比值來度量,公式如下:
??當集合A,B都為空時,J(A,B)定義為1。根據上述公式,當集合A和集合B兩者之間的交集越大時,表明兩者之間的相似程度越高。特別的,當集合A和集合B相同時,J(A,B)為1。因此:
J(A,B)∈[0,1]
廣義的Jaccard相似系數
??廣義的Jaccard相似系數也稱作Tanimoto系數,一般用EJ表示,公式如下:
??上述公式中的AB分別表示兩個向量,與俠義的Jaccrad中的元素為二值數據不同,廣義Jaccard可以使元素不僅是0或1,實質是狹義Jaccard系數的擴展。
2. 基于MinHash的相似性算法
??Minhash是一種基于Jaccard相關系數的快速對兩個幾個進行相似性分析的方法。該算法起初主要用于在搜索引擎中的重復網頁檢測,現在也大量應用于解決大規模聚類問題。
??在采用Jaccard系數進行相似度計算時,需要計算兩個集合的交集和并集,在海量維度場景下,計算的時間和空間復雜度都非常巨大。而Minhash在Jaccard的基礎上可以起到很好的降維效果。
??采用Minhash可以起到很好的減少計算復雜度的作用,其基本原理為:對于兩個集合A,B,在集合A和集合B的并集中選取元素的概率等于Jaccard系數。例如對于集合A={a, b, c},集合B={b,c,d},集合A和B的合集為{a,b,c,d},集合A和B的交集為{b,c},集合A和集合B的Jaccard系數為:0.5,而從交集{b,c}中挑選任何一個元素的概率也為:0.5,即與Jaccard系數相等。
??關于MinHash,先定義幾個符號術語:
??h(x): 把x映射成一個整數的哈希函數。
??hmin(S):集合S中的元素經過h(x)哈希后,具有最小哈希值的元素。
??那么對集合A、B,hmin(A) = hmin(B)成立的條件是A ∪ B 中具有最小哈希值的元素也在 A ∩ B中。這里有一個假設,h(x)是一個良好的哈希函數,它具有很好的均勻性,能夠把不同元素映射成不同的整數。所以有,Pr[hmin(A) = hmin(B)] = J(A,B),即集合A和B的相似度為集合A、B經過hash后最小哈希值相等的概率。
??基于以上結論,我們便可以根據MinHash來計算兩個集合的相似度了。一般有兩種方法:
??1:使用多個hash函數
??為了計算集合A、B具有最小哈希值的概率,我們可以選擇一定數量的hash函數,比如K個。然后用這K個hash函數分別對集合A、B求哈希值,對每個集合都得到K個最小值。比如Min(A)k={a1,a2,...,ak},Min(B)k={b1,b2,...,bk}。那么,集合A、B的相似度為|Min(A)k ∩ Min(B)k| / |Min(A)k ∪ Min(B)k|,即Min(A)k和Min(B)k中相同元素個數與總的元素個數的比例。
??2:使用單個hash函數
??第一種方法有一個很明顯的缺陷,那就是計算復雜度高。使用單個hash函數是怎么解決這個問題的呢?請看:前面我們定義過 hmin(S)為集合S中具有最小哈希值的一個元素,那么我們也可以定義hmink(S)為集合S中具有最小哈希值的K個元素。這樣一來我們就只需要對每個集合求一次哈希,然后取最小的K個元素。計算兩個集合A、B的相似度,就是集合A中最小的K個元素與集合B中最小的K個元素的交集個數與并集個數的比例。
3. 余弦相似度
??雖然MinHash減小了計算復雜度,但是實質上,Jaccard的理論基礎支持還不夠,因為僅僅依靠內部屬性是否出現去判定兩者是否相似并不夠精準。因此,產生了余弦相似度,它將屬性是否出現變更為屬性在樣本中的權重。余弦相似度是基于向量空間模型的算法,其關鍵字向量依賴于TF-IDF算法或者其他關鍵字提取算法。余弦相似度是通過計算兩個向量的夾角余弦值來評估他們的相似度。余弦相似度將向量根據坐標值,繪制到向量空間中,如最常見的二維空間。
余弦相似度的計算公式如下:
??余弦值的范圍在[-1,1]之間,值越趨近于1,代表兩個向量的方向越接近;越趨近于-1,他們的方向越相反;接近于0,表示兩個向量近乎于正交。
??最常見的應用就是計算文本相似度。將兩個文本根據他們詞,建立兩個向量,計算這兩個向量的余弦值,就可以知道兩個文本在統計學方法中他們的相似度情況。實踐證明,這是一個非常有效的方法。
4.基于SimHsh的相似性算法
??SimHash是一種局部敏感的哈希算法那,可以理解為指紋碼,此類指紋碼不同于其他哈希算法對應的指紋碼,指紋碼雖然幾乎唯一,但是SimHash可以使得相似的文本具有相似的哈希值。通過計算漢明距離,表達兩個文本之間的相似度。這是SIMHash最重要的特征。
??前面我們介紹了基于Jaccard相似系數、改進的MinHash,以及余弦相似度來度量樣本間的相似性。正常情況下,余弦相似度是一種比較可取的方式,但是在現實中,采用余弦相似度面臨的問題也越來越突出:
(1)余弦相似度兩兩計算的方式,效果雖然明顯,但是計算復雜度較高。
(2)通過關鍵詞的特征向量表達文本的特征,不易于存儲。
(3)在文本單詞較少時,可能會因為一兩個關鍵詞波動較大。
而SimHash可以很好的解決上述問題。
SimHash計算過程
- 分詞與權重計算。將詞語進行分詞處理,并計算每個分詞在文本中的權重。當所需處理的文本長度過長時,只需要按照權重由高到低篩選出前K個詞語即可,不需要將每個詞都納入計算。
- 哈希二進制計算。對詞語進行二進制轉換,轉換的結果可以是一個32位或64位的二進制值。
- 詞語加權。在步驟1中已經得到每個詞語在文中的權重,這些權重需要表現在其二進制內容中,將權重與詞語的二進制值進行按位乘法,不同點在于,遇到二進制值為0時乘以權重的負數,遇到二進制值為1時乘以權重的即可。
- 合并累計。對文本中的詞語進行加權計算之后,最終每個詞語都會產生加權值,這些值內容代表著該詞語在每個二進制位上的特征。若需計算文本的全局特征,只需將文本詞語的加權值進行合并累計,該過程即可理解為將加權值按照每一位進行求和。
- 降維輸出。步驟四的累加結果中,實質上已經產生了文本的特征碼,但是在絕對多數情況下,該特征碼不僅較長,而且內容也會各式各樣,會給特征比較帶來困難,因此,需要將特征碼進行降維輸出。降維的目的是降低特征碼的復雜度,約定位值小于0的為-1,大于等于0的為1,該值即為SimHash。
??SimHash目前主要用于重復信息的過濾,通過比較兩個文本的漢明距離來判定兩個文本的相似度。與余弦相似度相比,SimHash可以大大復雜文本的計算復雜度。