字符串编辑距离之LevenshteinDistance

概述

Levenshtein Distance是一个度量两个字符序列之间差异的字符串度量标准,两个单词之间的Levenshtein Distance是将一个单词转换为另一个单词所需的单字符编辑(插入、删除或替换)的最小数量。Levenshtein Distance是1965年由苏联数学家Vladimir Levenshtein发明的。Levenshtein Distance也被称为编辑距离(Edit Distance)。

定义

对于两个字符串ab,长度分别为\left | a \right |\left | b \right |,它们的Levenshtein Distance \operatorname{lev}_{a,b}(|a|,|b|)为:

\operatorname{lev}_{a,b}(i,j)=\left\{\begin{matrix} max(i,j)& \text{if min}(i,j)=0\\ min\left\{\begin{matrix} \operatorname{lev}_{a,b}(i-1,j)+1 \\ \operatorname{lev}_{a,b}(i,j-1)+1 \\ \operatorname{lev}_{a,b}(i-1,j-1)+1_{(a_{i}\neq b_{j})} \end{matrix}\right.& \text{otherwise} \end{matrix}\right. 

其中当a_{i}=b_{j}时,1_{(a_{i}\neq b_{j})}为0,否则为1。\operatorname{lev}_{a,b}(i,j)就是a的前i个字符与b的前j个字符的编辑距离。

ab的相似度Sim_{a,b}Sim_{a,b}=1-(\operatorname{lev}_{a,b}(\left | a \right |,\left | b \right |)/max(\left | a \right |,\left | b \right |))

原理

首先考虑极端情况,当ab长度为0时,那么需要编辑的次数就是里一个字符串的长度。

然后再考虑一般情况,此时分为三种情况:

  1. 在k个操作中,将a[1...i]转换为b[1...j-1]
  2. 在k个操作中,将a[1...i-1]转换为b[1...j]
  3. 在k个操作中,将a[1...i-1]转换为b[1...j-1]

针对第一种情况,只需要在a[1...i]后加上字符b[j],即可完成a[1..i]到b[1...j]的转换,总共需要的编辑次数即为k+1。

针对第二种情况,只需要在a[i]字符从a中移除,即可完成a[1..i]到b[1...j]的转换,总共需要的编辑次数即为k+1。

针对第三种情况,只需要将a[i]转换为b[j],即可完成a[1..i]到b[1...j]的转换,如果a[i]与b[i]的字符相同,则总共需要的编辑次数为k,否则即为k+1。

所以上述三种情况分别对应于插入、删除、替换操作。

为了保证将a[1..i]转换为b[1..j]的操作数总是最少的,只需要从三种情况中选择操作次数最少的情况,同理为了保证三种情况的操作数也是最小的,只需要按此逻辑进行迭代保证每一步的操作数都是最小的即可。

示例

为方便理解,以字符串a:abroad和b:aboard为例,将求值过程中每一步的操作数放入一个i+1行j+1列的二维数组d中,d[i,j] 即为将a[1..i]转换为b[1...j]所需要的最少的操作数。

1.首先是极端情况,即d[0][j]、d[i][0]即a为空字符串或b为空字符串时,需要操作的次数即为另一字符串的长度。

2.然后是一般情况,即d[i][j]的值,遍历这个二维数组,从第一行开始直到最后一行,由定义可知d[i][j]的值为d[i-1][j]+1、d[i][j-1]+1以及d[i-1][j-1]+1(如果a[i]==b[j])的最小值。即根据d[i][j]所在位置的正上方(d[i-1][j])、左方以(d[i-1][j])及左上方(d[i-1][j-1])的值计算出d[i][j]的值,由此得到二维数组中所有元素的值。

3.最后的d[i][j]即为字符串a转换为b的最少操作数。

求值过程如下图:
 

Levenshtein Distance

如图字符串ab的Levenshtein Distance \operatorname{lev}_{a,b}(6,6)为2,相似度Sim_{a,b}为:

Sim_{a,b}=1-(\operatorname{lev}_{a,b}(6,6)/max(6,6))=0.666\cdots

  • 1
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 5
    评论
Levenshtein Distance算法是一种常见的字符串相似度算法,也被称为编辑距离算法。其主要思想是通过计算两个字符串之间的编辑距离来确定它们的相似程度。 编辑距离指的是将一个字符串转换成另一个字符串所需的最少操作次数,其中每次操作可以是插入、删除或替换一个字符。例如,将字符串“kitten”转换成字符串“sitting”需要进行3次操作,即将“k”替换为“s”,将“e”替换为“i”,将“n”替换为“g”。 Levenshtein Distance算法的实现一般使用动态规划的方法,通过填充一个二维矩阵来计算两个字符串之间的编辑距离。具体实现过程可以参考以下伪代码: ``` function LevenshteinDistance(s1, s2): m = length(s1) n = length(s2) d = new matrix(m+1, n+1) for i from 0 to m: d[i, 0] = i for j from 0 to n: d[0, j] = j for j from 1 to n: for i from 1 to m: if s1[i] == s2[j]: cost = 0 else: cost = 1 d[i, j] = min(d[i-1, j]+1, d[i, j-1]+1, d[i-1, j-1]+cost) return d[m, n] ``` 在以上代码中,变量s1和s2分别表示两个待比较的字符串,m和n分别表示它们的长度,矩阵d用于存储编辑距离的计算结果。首先,将矩阵d的第一行和第一列分别初始化为0到n和0到m的整数。然后,对于每个(i, j)位置,如果s1[i]等于s2[j],则将cost设为0,否则设为1。最后,根据递推公式d[i, j] = min(d[i-1, j]+1, d[i, j-1]+1, d[i-1, j-1]+cost)来填充矩阵d,并返回d[m, n]作为编辑距离的结果。 Levenshtein Distance算法的时间复杂度为O(m*n),其中m和n分别为两个字符串的长度。在实际应用中,该算法可用于拼写检查、数据去重等场景。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值