- 实践题目
- 最短编辑距离问题
- 问题描述
- 设A和B是2个字符串。将字符串A转换为字符串B所要用到的最少的字符操作(对单个字符进行插删改)的次数称为字符串A到 B的编辑距离,记为d(A,B)。 对于给定的字符串A和字符串B,计算其编辑距离 d(A,B)。
- 算法描述
- 从A字符串(fxpimu)只有0个字符开始,只有增加的操作满足其转换为B串(xwrs)。(同样的B串转换为A串也是同样的)那么此时就需要用到一个二维数组c[n][n](灰色的部分)来存储这些操作数:
1 for (int i = 0; i <= len_a; ++i) { 2 c[i][0] = i; 3 } 4 for (int i = 0; i <= len_b; ++i) { 5 c[0][i] = i; 6 }
-
然后:运用动态规划的的思想,将问题层层递进(嵌套for循环),从只观察字符串的一个字符开始,直到所有的字符
-
如果此时A串和B串各增加一个相同的字符在末尾那么就相当于只用对该字符前面的字串进行操作。例如,fx 转换为x,只需要相当于 f转换为空的操作次数所以c[1][2] = c[0][1]
- 如果增加不同的字符,那么只需要在原基础增加一个操作数就能实现,所以就在c[i-1][j-1], c[i-1][j]+1和c[i][j-1]中选一个最少的操作数加一就行了
1 for (int i = 1; i <= len_a; ++i) // len_a = a.size();#include <cstring> 2 for (int j = 1; j <= len_b; ++j) { 3 if (a[i-1] == b[j-1]) { // 相同的字符 4 c[i][j] = c[i-1][j-1]; 5 } 6 else { // 不同的字符;min操作用到了#include <algorithm> 7 c[i][j] = min(c[i-1][j-1]+1, min(c[i-1][j]+1, c[i][j-1]+1)); 8 } 9 }
-
- 从A字符串(fxpimu)只有0个字符开始,只有增加的操作满足其转换为B串(xwrs)。(同样的B串转换为A串也是同样的)那么此时就需要用到一个二维数组c[n][n](灰色的部分)来存储这些操作数:
- 算法时间及空间复杂度分析(要有分析过程)
- 嵌套for循环:时间复杂度为O(N*M) N为len_a, M为len_b len_a = a.size();
- 新开了一个二维数组:空间复杂度为O(N*M) N为len_a, M为len_b
- 心得体会(对本次实践收获及疑惑进行总结)
- 动态规划真的有助于完成一些看似非常复杂,但是其子问题却不是很难的题目。