iT邦幫忙

2024 iThome 鐵人賽

DAY 27
0
AI/ ML & Data

From Python Beginner To AI Engineer系列 第 28

使用集合計算字串相似度

  • 分享至 

  • xImage
  •  

前一篇文章介紹了 Counter 類別,這個類別會對列表或字串中的相同元素做累加。然而有些時候,我們並不在意元素的出現次數,這時可以透過內建類別 set 集合來做統計:

>>> s = "庭院深深深幾許"
>>> set(s)
{'幾', '庭', '深', '許', '院'}

set 是不看順序而且元素必定唯一的,這個性質可以用來評估兩個集合的相似性。我們可以透過 & 運算來取兩個集合的交集

>>> s1 = set("蘋果真好吃")
>>> s2 = set("好吃的蘋果")
>>>
>>> print(s1)
>>> print(s2)
>>> print(s1 & s2)
{'真', '好', '果', '吃', '蘋'}
{'的', '好', '果', '吃', '蘋'}
{'吃', '好', '蘋', '果'}

| 運算則可以取兩個集合的聯集

>>> print(s1 | s2)
{'的', '真', '好', '果', '吃', '蘋'}

那這兩個字串的相似度,就可以表示為交集除以聯集

>>> intersection = s1 & s2
>>> union = s1 | s2
>>> len(intersection) / len(union)
0.6666666666666666

當兩個字串不相似時,這個分數就會很低:

>>> def similarity(s1, s2):
>>>     s1 = set(s1)
>>>     s2 = set(s2)
>>>
>>>     intersection = s1 & s2
>>>     union = s1 | s2
>>>
>>>     return len(intersection) / len(union)
>>>
>>> print(similarity("蘋果真好吃", "好吃的蘋果"))
>>> print(similarity("蘋果真好吃", "香蕉好難吃"))
0.6666666666666666
0.25

其實像這樣的交集與聯集的操作,同樣適用於 Counter 類別:

>>> from collections import Counter
>>>
>>> def similarity2(s1, s2):
>>>     s1 = Counter(s1)
>>>     s2 = Counter(s2)
>>>
>>>     intersection = sum((s1 & s2).values())
>>>     union = sum((s1 | s2).values())
>>>
>>>     return intersection / union
>>>
>>> print(similarity2("蘋果真好吃", "好吃的蘋果"))
>>> print(similarity2("蘋果真好吃", "好好吃的蘋果"))
>>> print(similarity2("蘋果真好吃", "香蕉好難吃"))
0.6666666666666666
0.5714285714285714
0.25

因為 Counter 做完交集與聯集的操作後,依然是個字典,所以使用 .values() 將所有統計值加總在一起,因此「好好吃的蘋果」會比「好吃的蘋果」更不相似於「蘋果真好吃」。


上一篇
如何統計字詞的出現頻率
下一篇
如何把檔案內容讀取出來?
系列文
From Python Beginner To AI Engineer31
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言