假设您已扫描带有名称的文档。由于扫描过程中的错误,您想在词典中查找名称。因此,您需要一个函数,该函数接受一个可能的名称并输出一个列表,该列表的输入的所有可能的字符串变化都应在Levenshtein-Distance为1的范围内。
我修改了一个实现(https://rosettacode.org/wiki/Levenshtein_distance#Python),但没有得到正确的结果。由于Levenshtein的实现通常会接受两个字符串并进行比较以给出L距离的整数,所以我想知道如何更改它以获取一个字符串的变体吗?
def levenshteinVariation(n_possible):
m = n_possible
n = n_correct
d = []
for i in range(len(m)+1):
d.append([i])
del d[0][0]
for j in range(len(n)+1):
d[0].append(j)
for j in range(1,len(n)+1):
for i in range(1,len(m)+1):
if m[i-1] == n[j-1]:
d[i].insert(j,d[i-1][j-1])
else:
minimum = min(d[i-1][j]+1, d[i][j-1]+1, d[i-1][j-1]+2)
d[i].insert(j, minimum)
return d
预期结果将是字典中L距离为1内的所有变体的匹配。
for n_correct, n_possible in [('Marcus','Maacus'), ('David','Davide'), ('Steve', 'Steven')]:
print(f"{n_correct} found: {n_correct in levenshteinVariation(n_possible)}")
但是我得到了
Marcus found: False
David found: False
Steve found: False
答案 0 :(得分:0)
感谢DanD。我能够自己解决它:
def Variations1(name):
letters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'
splits = [(name[:i], name[i:]) for i in range(len(name) + 1)]
deletes = [L + R[1:] for L, R in splits if R]
transposes = [L + R[1] + R[0] + R[2:] for L, R in splits if len(R) > 1]
replaces = [L + c + R[1:] for L, R in splits if R for c in letters]
inserts = [L + c + R for L, R in splits for c in letters]
return set(deletes + transposes + replaces + inserts)