如何求字符串的编辑距离

看过网上的多篇文章,图示的基本都是列表格的,看的晕敷敷的。最终还是自己用动态规划的思想给推出来的,所以从基本思想入手,一点点推导,或许比直接看人家的推导结果更有效。

参考书籍:《Python程序员面试算法宝典》
在这里插入图片描述
用动态规划的思想分析。下面的操作均是执行在字符串s1上。

  • 添加
    假设,字符串s1的i个字符构成的字符串,和字符串s2的j-1个字符构成的字符串,两个字符串的编辑距离 D(i,j-1) 已知,即s1比s2少一个字符。那么只需s1的末尾添加字符s2[j]即可。s1[i]—(变换到)—>s2[j]的编辑距离为D(i,j) = D(i,j-1)+1。
    在这里插入图片描述

  • 删除
    假设,字符串s1的前i-1个字符构成的字符串,和字符串s2的j个字符构成的字符串,两个字符串的编辑距离 D(i-1,j) 已知,即s1比s2多一个字符。那么只需删除s1的最后一个字符即可。s1[i]—(变换到)—>s2[j]的编辑距离为D(i,j) = D(i-1,j)+1。

  • 替换
    假设,字符串s1的前i-1个字符构成的字符串,和字符串s2的前j-1个字符构成的字符串,两个字符串的编辑距离 D(i-1,j-1) 已知,即s1与s2仅最后一个字符还没匹配。那么将s1变换到s2需要什么操作呢?

    • s1[i] == s2[j]
      s1与s2的最后一个字符相同时,不需要进行操作。s1[i]—(变换到)—>s2[j]的编辑距离为D(i,j) = D(i-1,j)。
    • s1[i] ̸ = \not= ̸=s2[j]
      s1与s2的最后一个字符不同时,只需将s1的最后一个字符替换为s2[j]。s1[i]—(变换到)—>s2[j]的编辑距离为D(i,j) = D(i-1,j)+1。

综上,编辑距离的计算如下:

  • 两个字符串中有空串

    • 只有s1是空串,那么D(i,j)=j,即一直向s1添加字符。
    • 只有s2是空串,那么D(i,j)=i。
    • s1、s2都是空串,那么D(i,j)=0。
  • 两个字符串都不是空串
    s1、s2的最后一个字符可以通过如下方式,变换为相同。

    • 添加,D(i,j) = D(i-1,j)+1
    • 删除,D(i,j) = D(i,j-1)+1
    • 替换。最后一个字符相同时,D(i,j)=D(i-1,j-1)。最后一个字符不同时,D(i,j)=D(i-1,j-1)+1。

    所以 D ( i , j ) = m i n { D ( i − 1 , j ) + 1 , D ( i , j − 1 ) + 1 , f ( i , j ) } D(i,j)=min\left\{D(i-1,j)+1,D(i,j-1)+1,f(i,j)\right\} D(i,j)=min{D(i1,j)+1D(i,j1)+1f(i,j)},当s1[i]==s[j]时,f(i,j)==D(i-1,j-1)。当s1[i] ̸ = \not= ̸=s[j]时,f(i,j)=D(i-1,j-1)+1。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

张之海

若有帮助,客官打赏一分吧

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值