按给定短语返回匹配项列表
问题内容:
我正在尝试一种方法,可以检查给定的短语是否与短语列表中的至少一项匹配并返回它们。输入是短语,短语列表和同义词列表的字典。关键是要使其通用。
这是示例:
phrase = 'This is a little house'
dictSyns = {'little':['small','tiny','little'],
'house':['cottage','house']}
listPhrases = ['This is a tiny house','This is a small cottage','This is a small building','I need advice']
我可以创建一个可以在返回bool的示例中执行此操作的代码:
if any('This'+' '+'is'+' '+'a'+x+' '+y == phrase for x in dictSyns['little'] for y in dictSyns['house']):
print 'match'
第一点是我必须创建通用的函数(取决于结果)。第二个是我希望此函数返回匹配短语的列表。
您能否给我一个建议,以使方法['This is a tiny house','This is a small cottage']
在这种情况下返回?
输出如下:
>>> getMatches(phrase, dictSyns, listPhrases)
['This is a tiny house','This is a small cottage']
问题答案:
我将按以下方式进行处理:
import itertools
def new_phrases(phrase, syns):
"""Generate new phrases from a base phrase and synonyms."""
words = [syns.get(word, [word]) for word in phrase.split(' ')]
for t in itertools.product(*words):
yield ' '.join(t)
def get_matches(phrase, syns, phrases):
"""Generate acceptable new phrases based on a whitelist."""
phrases = set(phrases)
for new_phrase in new_phrases(phrase, syns):
if new_phrase in phrases:
yield new_phrase
代码的根本是words
in中的分配new_phrases
,它将phrase
和syns
转换为更可用的形式,一个列表,其中每个元素都是该单词可接受的选择的列表:
>>> [syns.get(word, [word]) for word in phrase.split(' ')]
[['This'], ['is'], ['a'], ['small', 'tiny', 'little'], ['cottage', 'house']]
请注意以下几点:
- 使用生成器更有效地处理大量组合(而不是一次构建整个列表);
- 使用a
set
进行有效的(O(1)
,而O(n)
不是列表)成员资格测试; - 使用
itertools.product
生成phrase
基于的可能组合syns
(您也可以itertools.ifilter
在实现中使用);和 - 符合风格指南。
正在使用:
>>> list(get_matches(phrase, syns, phrases))
['This is a small cottage', 'This is a tiny house']
要考虑的事情:
- 字符的情况如何(例如应如何
"House of Commons"
对待)? - 标点符号呢?