0
点赞
收藏
分享

微信扫一扫

大语言模型:Query Rewriting for Retrieval-Augmented Large Language Models

大家好,自然语言处理会涉及到一致性验证特征。英文的姓名相似度包含用户自己填写的姓名、身份证上ocr识别的姓名、征信报告中用户姓名,可以作为模型特征使用、也可以作为业务的个人信息验证规则使用,本文简单介绍其计算逻辑。

1.原理

编辑距离,又叫Levenshtein距离。对于两个字符串文本序列,根据 Levenshtein 计算将一个序列更改为另一个序列所需的最小插入、删除和替换次数,以及插入、删除和替换的自定义成本。

如 "lewenstein"、"levenshtein"的编辑距离为2,"lewenstein" 需要通过一次替换(第三位字符"w"替换为"v")、一次插入("s"字符后插入"t"),即可变为"levenshtein"。

编辑距离越小,一个字符串变更为另一个字符串的变更次数越小,两个字符串的相似度也就越高。可以看出编辑距离非常适合用于计算英文的姓名相似度,在客户自己填写个人信息时,可能会有部分缩写,如"Travor Noah"缩写为"Noah, T.",也可能将"levenshtein"错误拼写为"lewenstein"(ocr识别出姓名的此类问题更是常见),而编辑距离能够很好地减缓这种问题所造成的姓名不一致。

2.工具包

编辑距离的计算可以直接调用levenshtein包,不仅实现了编辑距离及归一化的相似度,还实现了hamming距离和jaro距离计算。

pip install levenshtein https://pypi.tuna.tsinghua.edu.cn/simple your_package

3.参数解释

3.1 编辑距离
Levenshtein.distance(s1, s2, *, weights=(1, 1, 1), processor=None, score_cutoff=None)

s1 ( Sequence [ Hashable ] ) :要比较的第一个字符串。

s2 ( Sequence [ Hashable ] ) :要比较的第二个字符串。

weights ( Tuple [ int , int , int ] or None , optional ):三种操作的权重(插入、删除、替换)。默认值为 (1, 1, 1),即插入1次、删除1次、替换1次,计算的编辑距离均为1,可自定义。

processor ( callable , optional ):可选参数,用于在比较字符串之前对其进行预处理,默认不使用。

score_cutoff ( int , optional ):设定s1 和 s2 之间的最大距离限制,如果编辑距离大于score_cutoff,则返回 score_cutoff + 1。默认为无,不使用最大距离限制。

3.2 编辑距离相似度

归一化的编辑距离:将编辑距离归一化,使得相似度取值范围在[0,1]内,越接近于1、相似度越高。注意此处字符的插入、删除、替换权重为(1, 1, 2)。

Levenshtein.ratio(s1, s2, *, processor=None, score_cutoff=None)

processor ( callable , optional ):可选参数,用于在比较字符串之前对其进行预处理,默认不使用。

score_cutoff ( float , optional ):分数阈值的可选参数,作为 0 到 1.0 之间的浮点数。对于norm_sim < score_cutoff返回0,否则返回1。默认值为 0、不使用cutoff。

3.3 Hamming距离

汉明距离的计算要求比较的两个字符串长度相同,逻辑为两个字符串对应位置上不同的字符个数。

Levenshtein.hamming(s1, s2, *, processor=None, score_cutoff=None)

processor ( callable , optional ):可选参数,用于在比较字符串之前对其进行预处理。默认不使用。

score_cutoff ( int or None , optional ):设置 s1 和 s2 之间的最大距离限制。如果距离大于 score_cutoff,则返回 score_cutoff + 1。默认为无,不使用cutoff。

4.姓名相似度

有了编辑距离归一化的相似度,可以用于计算英文名的姓名相似度,但是需要注意的是经常会有名字顺序颠倒的情况,这时候直接套用Levenshtein.ratio是有明显问题的。

import Levenshtein
Levenshtein.distance("lewenstein", "levenshtein")
# 2

Levenshtein.ratio("lewenstein", "levenshtein")
# 0.8571428571428572

Levenshtein.ratio("steven zhou", "zhou steven")
# 0.5454545454545454

针对姓名first、median、last name顺序错乱颠倒的问题,可以把两个姓名的first、median、last name进行排序处理:按照空格分割、对分割结果的list进行升序排序、再拼接为字符串,这样就可以避免,然后再进行比较就可以了。

def split_sort(string):
    result=' '.join(sorted(string.split()))
    return result
print(split_sort('zhou steven'))
print(split_sort('steven zhou'))
# steven zhou
# steven zhou

Levenshtein.ratio("steven zhou", "zhou steven")
# 0.5454545454545454

Levenshtein.ratio(split_sort("steven zhou"), split_sort("zhou steven"))
# 1.0
举报

相关推荐

0 条评论