簡體   English   中英

合並類似的字符串Python

[英]Merge Similar Strings Python

我有兩個琴弦

string1 = "apple banna kiwi mango"
string2 = "aple banana mango lemon"

我想要將這兩個字符串相加(而不是串聯)的結果,即結果應該像

result = "apple banana kiwi mango lemon"

我當前的方法很簡單。

  1. 標記多行字符串(以上字符串在標記化之后),消除所有噪音(特殊/換行符/空字符串)
  2. 下一步是確定字符串的余弦相似度,如果大於0.9,則將字符串之一添加到最終結果中

現在,這就是問題所在。 它不涵蓋其中一個字符串包含一個單詞的一半而另一字符串包含單詞的另一半(在某些情況下為正確的單詞)的部分。 我還在腳本中添加了功能。 但是問題仍然存在。 感謝您提供任何有關如何繼續前進的幫助。

def text_to_vector(text):
     words = WORD.findall(text)
     return Counter(words)

def get_cosine(vec1, vec2):
     intersection = set(vec1.keys()) & set(vec2.keys())
     numerator = sum([vec1[x] * vec2[x] for x in intersection])

     sum1 = sum([vec1[x]**2 for x in vec1.keys()])
     sum2 = sum([vec2[x]**2 for x in vec2.keys()])
     denominator = math.sqrt(sum1) * math.sqrt(sum2)

     if not denominator:
        return 0.0
     else:
        return float(numerator) / denominator


def merge_string(string1, string2):
    i = 0
    while not string2.startswith(string1[i:]):
        i += 1

    sFinal = string1[:i] + string2
    return sFinal

for item in c:
for j in d:
    vec1 = text_to_vector(item)
    vec2 = text_to_vector(j)
    r = get_cosine(vec1, vec2)
    if r > 0.5:
        if r > 0.85:
            final.append(item)
            break
        else:
            sFinal = merge_string(item, j)
            #print("1.", len(sFinal), len(item), len(j))
            if len(sFinal) >= len(item) + len(j) -8:
                sFinal = merge_string(j, item)
                final.append(sFinal)
                #print("2.", len(sFinal), len(item), len(j))
                temp.append([item, j])
                break

困難的部分是檢查單詞是否為有效的英語單詞。

為此,您必須擁有字典來對照該單詞,或者使用nltk。

     pip install nltk  

     from nltk.corpus import wordnet  

     set([w for w in (string1 + string2).split() if  wordnet.synsets(w)]) 

     Out[41]: {'apple', 'banana', 'kiwi', 'lemon', 'mango'}

要捕獲數字(如果存在),請添加isdigit()。

st1 = 'Includes Og Added Sugars'

st2 = 'Includes 09 Added Sugars 09'


set([w for w in (st1 + st2).split() if  (wordnet.synsets(w) or w.isdigit())])

Out[30]: {'09', 'Added', 'Includes', 'Sugars'}

要捕獲g等縮寫,請添加re.match()。

set([w for w in (st1 + st2).split() if  (wordnet.synsets(w) or w.isdigit() or re.match(r'\d+g|mg',w))])

Out[40]: {'09', '0g', 'Added', 'Includes', 'Sugars'}

您聽說過Levenshtein的距離嗎? 我建議以下算法:

  1. 將列表拆分為元素(string1.split(“”))

  2. 遍歷list(string1) 在其中循環遍歷list(string2) ,如果說兩個元素的Levenshtein距離小於3,則將該元素推入結果數組。

  3. 返回result

for i in list(string1): for k in list(string2): if levenshtein(i,k) < 3: res.append(i)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM