问题:
难度:Hard
说明:
给出两个字符串String01,String02,将String01修改为String02需要多少步骤?你可以将字符串进行增加,删除,修改操作。
输入案例:
Example 1:
Input: word1 = "horse", word2 = "ros"
Output: 3
Explanation:
// 将h修改为r,变成rorse
horse -> rorse (replace 'h' with 'r')
// 将r移除,变成 rose
rorse -> rose (remove 'r')
// 将e移除,变成ros,得出结果
rose -> ros (remove 'e')
Example 2:
Input: word1 = "intention", word2 = "execution"
Output: 5
Explanation:
intention -> inention (remove 't')
inention -> enention (replace 'i' with 'e')
enention -> exention (replace 'n' with 'x')
exention -> exection (replace 'n' with 'c')
exection -> execution (insert 'u')
我的代码:
其实就一个dp的问题,难的地方是理解怎么去状态转移,单纯看代码你是看不懂什么意思的,需要把增删改三个状态理解并且变成一个dp公式。状态转换方程应该如下(拿别人的):dp[i - 1][j - 1]是修改操作
public class EditDistance {
public static void main(String[] args) {
Solution solution = new EditDistance().new Solution();
String ss01 = "horse";
String ss02 = "ros";
System.out.println(solution.minDistance(ss01,ss02));
}
class Solution {
public int minDistance(String word1, String word2) {
int len01 = word1.length();
int len02 = word2.length();
char[] chars1 = word1.toCharArray();
char[] chars2 = word2.toCharArray();
// A:根据算法需要把所有字符遍历需要长度+1
int[][] dp = new int[len01 + 1][len02 + 1];
// 记忆化搜索
// 第一列增加操作
for(int i = 0;i <= len01;i ++) {
dp[i][0] = i;
}
// 第一行删除操作
for(int i = 0;i <= len02;i ++) {
dp[0][i] = i;
}
for(int i = 1; i <= len01; i++) {
for(int j = 1; j <= len02; j++) {
// 根据A: 操作数 = 判断上一行列字符,如果相等为0,不进行修改
int op = chars1[i - 1] == chars2[j - 1] ? 0 : 1;
// 选择最小操作数
dp[i][j] = Math.min(op + dp[i - 1][j - 1],
Math.min(dp[i - 1][j] + 1, dp[i][j - 1] + 1));
}
}
return dp[len01][len02];
}
}
}