正则表达式:有效匹配除最后一个字符外的相同单词

时间:2017-02-04 00:38:50

标签: python python-3.x

如何有效匹配除最后一个字母之外的相同字词?

data = ['ades', 'adey', 'adhere', 'adherent', 'admin', 'admit', 'adverb', 'advert', 'adipocere', 'adipocerous', 'adjoining', 'adjoint', 'adjudicate', 'adjudication', 'adjunct']

实际数据较长,下面的实现需要很长时间才能运行:

temp_data = data 
count = 0
matches = {}
while count < len(data):
    for word in data:
        if word[:-1] == data[count][:-1] and data.index(word) != count:
            matches[data[count]] = word
            temp_data.remove(data[count])
            temp_data.remove(word)
    count += 1
print(matches)

这正确打印:

{'ades': 'adey', 'advert': 'adverb', 'admin': 'admit'}

我是python的新手,所以任何建议都会受到赞赏:)

2 个答案:

答案 0 :(得分:4)

您将每个单词与每个单词进行比较,并使用每次比较每个单词的检查,以确保您在O(n³)时间内不会将单词与自身进行比较。您可以通过跟踪内循环中的索引来获得O(n²)时间:

for j, word in enumerate(data):
    if word[:-1] == data[count][:-1] and j != count:
        matches[data[count]] = word
        temp_data.remove(data[count])
        temp_data.remove(word)

然后通过将单词按其首字母分组来获取O(n):

groups = defaultdict(list)

for word in data:
    groups[word[:-1]].append(word)

print(list(groups.values()))

如果您的列表已排序,也可以使用groupby完成:

import itertools

def init(word):
    return word[:-1]

print([list(words) for key, words in itertools.groupby(data, init)])

答案 1 :(得分:1)

假设已经对list进行了排序(否则您需要先对其进行排序),并且在该标准之后的列表中只有两个这样的元素。您可以使用字典理解zip来实现结果:

>>> data = ['ades', 'adey', 'adhere', 'adherent', 'admin', 'admit', 'adverb', 'advert', 'adipocere', 'adipocerous', 'adjoining', 'adjoint', 'adjudicate', 'adjudication', 'adjunct']

# data.sort()  --> if data is not already sorted
>>> {i: j for i, j in zip(data, data[1:]) if i[:-1]==j[:-1]}
{'admin': 'admit', 'adverb': 'advert', 'ades': 'adey'}

PS:我认为regex不是实现理想结果的正确工具。