2011-10-31 29 views
0

例子:匹配字符串(Python)中的單詞的有效方法是什麼?

1. names = ['James John', 'Robert David', 'Paul' ... the list has 5K items] 
2. 
3. text1 = 'I saw James today' 
4. text2 = 'I saw James John today' 
5. text3 = 'I met Paul' 
6. 
7. is_name_in_text(text1,names) # this returns false 'James' in not in list 
8. is_name_in_text(text2,names) # this returns 'James John' 
9. is_name_in_text(text3,names) # this return 'Paul' 

is_name_in_text()如果有名單的是文本搜索。

簡單的方法是使用'in'運算符來檢查名稱是否在列表中,但列表中有5,000個項目,所以效率不高。我可以將文本拆分爲單詞,並檢查單詞是否爲in列表,但如果您有多個單詞匹配,則這不起作用。在這種情況下,第7行將失敗。

+0

您是否已經有了一種將名稱拉出短語的機制? –

+0

是的,我可以做出改變。它也可以在字典中。 '['詹姆斯約翰':'詹姆斯約翰']' – Sam

+1

恰好提出的問題。顯示測試數據的好工作。 –

回答

2

名稱轉換爲set並使用in-operator進行快速O(1)查找。

您可以使用正則表達式在一個句子解析出可能的名字:

>>> import re 
>>> findnames = re.compile(r'([A-Z]\w*(?:\s[A-Z]\w*)?)') 
>>> def is_name_in_text(text, names): 
     for possible_name in set(findnames.findall(text)): 
      if possible_name in names: 
       return possible_name 
     return False 

>>> names = set(['James John', 'Robert David', 'Paul']) 
>>> is_name_in_text('I saw James today', names) 
False 
>>> is_name_in_text('I saw James John today', names) 
'James John' 
>>> is_name_in_text('I met Paul', names) 
'Paul' 
+0

如何在''我今天看到詹姆斯約翰'中用'in'去搜索'set'(['James John','Robert David',...])''? –

+0

編輯答案以顯示捕獲文本輸入中名稱的正則表達式。 –

+0

下面是你的一個反例句:'「對於約翰·詹姆斯,這不起作用。」' –

1

您可以使用,而在操作使用Python的set,以獲得良好的性能。

1

如果您有一種將名稱拉出短語並且不必擔心部分匹配(全名始終位於字符串中)的機制,則可以使用一組而不是一個列表。

你的代碼是完全一樣的,但增加了第2行:

names = set(names) 

in操作現在可以正常快得多。

1

使用所有替代方法構建正則表達式。這樣你就不必擔心事先將這些名字從這些短語中拉出來。

import re 
names_re = re.compile(r'\b' + 
         r'\b|\b'.join(re.escape(name) for name in names) + 
         r'\b') 

print names_re.search('I saw James today') 
+0

這是一個很好的答案,雖然它確實爲5000+以上的相當大的正則表達式:-) –

+0

這是一個問題嗎?編譯正則表達式需要一些時間(我爲15000+個名字獲得了第二個),但搜索幾乎是即時的。 –

相關問題