形式陈述
两个版本的文字不同,差异可能来自换字,也可能来自插入一个字以后整体错位。怎样同时允许这两种变化,并找到费用最小的改写过程?
设 、 是同一字母表上的两个有限词公理库字Word · String从某个有限位置集到字母表的函数,即有限符号序列。。允许删除一个字符、插入一个字符、把一个字符替换成另一个,每次费用为 ;相等字符直接配对,费用为 。Levenshtein 编辑距离是把 变成 所需的最小总费用。本页不把交换相邻字符当作一次操作。
令 表示把前缀 改成 的距离。空前缀给出边界 、;内部按
计算。方括号中的命题为真时取 ,否则取 。先填第零行与第零列,再按行递增填表,返回 。
这份动态规划公理库动态规划Dynamic programming在有限或良基的状态依赖上复用已计算结果的算法设计范式。同时支持重建:从 出发,选择一条使上式取等号的前驱边,记录对应操作,直到 ,最后把记录倒序。本页固定“先对角,再删除,最后插入”的平局规则,使输出可复核;最小费用本身不依赖这条规则。
直觉
格点 的含义是:源串前 个字符已经消耗,目标串前 个字符已经生成。向下走只消耗源字符,是删除;向右走只生成目标字符,是插入;沿对角走同时消耗和生成,是配对或替换。所有边都增加 ,所以网格是一个有向无环图公理库有向无环图Directed acyclic graph · DAG不含有向环的有向图。,可以按拓扑次序求最短路。
为什么只看最后一步就够了?一条对齐路径到达 ,最后必然来自这三个前驱之一。若到那个前驱的部分并非最优,换成更便宜的部分不会影响最后一步,整条路径就还能变好。因此每个格子都由已经正确的较小前缀推出。归纳开始于空串边界,结束于右下角。
两条费用为 2 的对齐路径 “脚本”最好用消耗与生成的方式保存,而不是把每条命令都写成对当前字符串的绝对下标。前面的删除会移动后面的下标;对齐操作流则只维护两个游标。配对或替换读一个源字符并写一个目标字符,删除只读,插入只写,含义不会随执行进度漂移。
例子与边界
同样最优的两种解释
取 、。完整表如下,行、列标题中的空字符表示长度为零的前缀。
|
空 |
C |
A |
T |
C |
U |
S |
| 空 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
| C |
1 |
0 |
1 |
2 |
3 |
4 |
5 |
| A |
2 |
1 |
0 |
1 |
2 |
3 |
4 |
| C |
3 |
2 |
1 |
1 |
1 |
2 |
3 |
| T |
4 |
3 |
2 |
1 |
2 |
2 |
3 |
| U |
5 |
4 |
3 |
2 |
2 |
2 |
3 |
| S |
6 |
5 |
4 |
3 |
3 |
3 |
2 |
在 ,前缀 CAC 对 CAT 的最后字符不同。对角候选为 ,删除、插入候选都为 ,所以此格取 。到 时,三种候选都为 ,出现真正的解释歧义。
按本页的回溯顺序,保留前两个字符,把第三位 C 换成 T、第四位 T 换成 C,再保留 US,得到费用 的脚本。另一个同费脚本是删除第三位 C,得到 CATUS,再在 T 后插入 C。两条路径告诉我们:编辑距离认证最少操作数,不会自动判断现实中作者究竟做了哪一种修改。
为什么不是 ?两串长度相同,一次插入或删除无法保持长度;一次替换只能改变一个位置,而第三、第四位都不同。这给出下界 ,与脚本上界相遇。
先固定操作,再谈“距离”
若加入“相邻转置费用 ”,此例就会变成 ,需要另一套递推或状态;不能仍用三向公式然后把结果称作含转置的距离。若只允许等长逐位替换,得到的是Hamming 距离公理库Hamming 距离Hamming distance等长字中不同坐标的数量;由逐位比较、三角不等式和 Hamming 球解释检错与唯一纠错半径。;它无法解释一次插入引起的后续错位。精确字符串匹配公理库字符串匹配String matching · Exact pattern matching在文本中定位模式串全部出现位置的问题。又是在文本里找原样出现的位置,目标不是把两个整串改成相同。
带权对齐可以把三种边的 换成相应费用,空串边界改成累计插删费用。此时计算的是规定网格模型下的最小对齐费用。若还希望它等于允许任意连续改写的费用,要排除“先把一个字符换成第三种字符,再换成目标字符更便宜”等捷径,或先对字符操作费用做最短路闭包;对称性、正定性也不能由非负费用自动得到。
推论与应用
填表需要 时间、 存储;常写的 默认两串都非空。回溯至多走 步。只求距离时,每格只依赖当前行左邻与上一行,交换两串让短串作为列维后,可把工作数组压到 。但覆盖旧行也会丢掉回溯所需的前驱,不能直接宣称同样空间里还保有整份脚本。
Hirschberg 分解公理库Hirschberg 线性空间序列比对Hirschberg algorithm · Linear-space sequence alignment用前向与反向滚动行认证最优路径的中线穿越点,释放分数数组后递归重建完整对齐。用前向、反向滚动行找出最优路径的中间穿越点,再递归恢复脚本。若应用规定只有插入和删除,并且差异很少,Myers 算法公理库Myers 最短插删脚本算法Myers O(ND) algorithm · Shortest edit script按插删次数扩展编辑图的最远对角前沿,在差异较小时避免填满网格,并记录蛇形匹配段重建脚本。则按修改数扩展前沿,避免填满网格。前者主要节省重建存储,后者利用小差异参数;两者解决的问题条件不同。
比较两个实现时,先检查脚本实际生成了目标串,再检查费用最优。相同距离而脚本不同常常只是平局规则不同,不能仅据此判错。包含空串、重复字符、全相等、全不同以及插删优于替换的例子,才能覆盖边界和回溯分支。
参考资料
- Antti Laaksonen, Competitive Programmer’s Handbook, Chapter 7, “Edit distance”, printed pp. 74–75:作者公开教材。前缀递推、表格与路径重建。
- Dave Mount, CMSC 451 Lecture 9, “Longest Common Subsequence and Edit Distance”, Spring 2025, pp. 5–8:官方讲义。三类操作、空串边界及编辑递推。
- Robert A. Wagner and Michael J. Fischer, “The String-to-String Correction Problem”, Journal of the ACM 21(1), 1974, pp. 168–173:论文记录。插入、删除与替换的经典问题和算法。