Cover image for 面试经典150题 P72 编辑距离

面试经典150题 P72 编辑距离


时间轴

时间轴

2025-12-16

init

动态规划

题目:

这题和最长公共子序列类似:

dp[i][j]dp[i][j] 表示将 word1 的前 i 个字符转换为 word2 的前 j 个字符所需的最小操作数。

  • 初始化:
    • word1[0..=i]变为空字符需要 i 次操作,因此 dp[i][0]=idp[i][0] = i
    • 空字符串变为 word2[0…=j]需要 j 次操作,因此dp[0][j]=jdp[0][j] = j
  • 对于dp[i][j], i,j1i,j \ge 1,有:
    • 如果word[i-1]==word[j-1],那么不需要操作,dp[i][j]=dp[i1]dp[j1]dp[i][j]=dp[i-1]dp[j-1]
    • 否则 dp[i][j]=min(dp[i][j1],dp[i1][j],dp[i1][j1])+1dp[i][j] = min( dp[i][j - 1], dp[i - 1][j], dp[i - 1][j - 1] ) + 1
      • dp[i1][j]+1dp[i-1][j]+1 , 表示删除word1[i-1]
      • dp[i][j1]+1dp[i][j-1]+1 , 表示插入word2[j-1]
      • dp[i1][j1]+1dp[i-1][j-1]+1 , 表示替换word1[i-1]word2[j-1]
123456789101112131415161718192021222324252627282930313233343536373839404142434445
#include <string>#include <vector>#include <algorithm>using std::string;using std::vector;class Solution {    public:        int minDistance(string word1, string word2)        {                // 设 dp[i][j] 表示将 word1 的前 i 个字符转换为 word2 的前 j 个字符所需的最小操作数。                int i, j;                int m = word1.length(), n = word2.length();                vector<vector<int> > dp(m + 1, vector<int>(n + 1, 0));                for (i = 0; i <= m; i++) {                        // word1[0..=i]变为空字符需要i次操作                        dp[i][0] = i;                }                for (j = 0; j <= n; j++) {                        // 空字符串变为word2[0..=j]需要j次操作                        dp[0][j] = j;                }                for (i = 1; i <= m; i++) {                        for (j = 1; j <= n; j++) {                                if (word1[i - 1] == word2[j - 1]) {                                        // 不需要额外操作                                        dp[i][j] = dp[i - 1][j - 1];                                } else {                                        // dp[i-1][j](删除 word1[i-1])                                        // dp[i][j-1](插入 word2[j-1])                                        // dp[i-1][j-1](替换 word1[i-1] 为 word2[j-1])                                        dp[i][j] = std::min({ dp[i][j - 1], dp[i - 1][j],                                                              dp[i - 1][j - 1] }) +                                                   1;                                }                        }                }                return dp[m][n];        }};

leetcode hot 100 rewrite

1234567891011121314151617181920212223242526272829303132333435
#include <string>#include <vector>#include <algorithm>using std::string;using std::vector;class Solution {    public:        int minDistance(string word1, string word2)        {                int i, j, n1 = word1.size(), n2 = word2.size();                // dp[i][j] 表示word1[0..i)变成word2[0..j)的的最少步数                vector<vector<int> > dp(n1 + 1, vector<int>(n2 + 1, 0));                for (i = 0; i <= n1; i++)                        dp[i][0] = i;                for (j = 0; j <= n2; j++)                        dp[0][j] = j;                for (i = 1; i <= n1; i++) {                        for (j = 1; j <= n2; j++) {                                if (word1[i - 1] == word2[j - 1]) {                                        dp[i][j] = dp[i - 1][j - 1];                                } else {                                        dp[i][j] = std::min({ dp[i][j - 1], dp[i - 1][j],                                                              dp[i - 1][j - 1] }) +                                                   1;                                }                        }                }                return dp[n1][n2];        }};
评论加载中…