雁过无痕

  C++博客 :: 首页 :: 新随笔 :: 联系 :: 聚合  :: 管理 ::

《编程之美》读书笔记113.3 计算字符串的相似度

 

很经典的可使用动态规划方法解决的题目,和计算两字符串的最长公共子序列相似。

Ai为字符串A(a1a2a3 … am)的前i个字符(即为a1,a2,a3 … ai

Bj为字符串B(b1b2b3 … bn)的前j个字符(即为b1,b2,b3 … bj

L(i , j)为使两个字符串和AiBj相等的最小操作次数。

ai等于bj时 显然L(i, j)=L(i-1, j-1)

ai不等于bj

  若将它们修改为相等,则对两个字符串至少还要操作L(i-1, j-1)

  若删除ai或在Bj后添加ai,则对两个字符串至少还要操作L(i-1, j)

  若删除bj或在Ai后添加bj,则对两个字符串至少还要操作L(i, j-1)

  此时L(i, j)=min( L(i-1, j-1), L(i-1, j), L(i, j-1) )  + 1

 

显然,L(i, 0)=iL(0, j)=j, 再利用上述的递推公式,可以直接计算出L(i, j)值。

为了保持与书中代码一致,下面的函数参数类型是string,而不是char*

 

distance_1

由于只要求计算两字串的距离,计算时,只用到两列数据,因而可以对代码进一步优化,节省空间。


distance_2

 

上面的代码还可进一步优化,比如通过指针而不是数组名来访问内存。如果内存足够大,可以多申请空间,每次循环,通过修改保存的数据起始位置,避免内存复制。

 

补充:字符串的相似度,就是求编辑距离(edit distance)。



posted on 2010-08-16 00:21 flyinghearts 阅读(1355) 评论(0)  编辑 收藏 引用 所属分类: 编程之美

只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理