1- 思路
题目识别
- 识别1 :两个字符串之间相互转换,增、删、替换 最少的操作次数
动规五部曲
- 1- 定义 dp 数组
dp[i][j]
代表,长度为 i-1
的 nums1
和长度为 j-1
的 nums2
的编辑距离,也就是使二者相等的最小操作次数
- 2- 递推公式
- 如果两个字符相同了
dp[i][j] = dp[i-1][j-1]
,因为相同所以不需要任何操作 - 否则
- 删除 word1 操作:
dp[i-1][j] + 1
- 删除 word2 操作:
dp[i][j-1] + 1
- 替换操作:
dp[i-1][j-1] + 1
- 因此
dp[i][j] = Math.min(dp[i-1][j] + 1,Math.min(dp[i][j-1]+1,dp[i-1][j-1]+1);
- 3- 初始化
- 第一行、第一列初始化为对应的下标。
i
从 1
遍历到 len1
比如 dp[i][0]
则初始化为i
- 4- 递推
- 由于
[i][j]
根据 [i-1][j-1]
来,所以从上到下,从左到右遍历
2- 实现
⭐72. 编辑距离——题解思路
![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/37b2d72e171d46758db52400f7bb375b.png)
public int minDistance(String word1, String word2) {
int[][] dp = new int[word1.length() + 1][word2.length() + 1];
for (int i = 0; i <= word1.length(); i++) {
dp[i][0] = i;
}
for (int j = 0; j <= word2.length(); j++) {
dp[0][j] = j;
}
for (int i = 1; i <= word1.length(); i++) {
for (int j = 1; j <= word2.length(); j++) {
if (word2.charAt(j - 1) == word1.charAt(i - 1)) {
dp[i][j] = dp[i - 1][j - 1];
} else {
dp[i][j] = Math.min(dp[i - 1][j] + 1, Math.min(dp[i][j - 1] + 1, dp[i - 1][j - 1] + 1));
}
}
}
return dp[word1.length()][word2.length()];
}
3- ACM 实现
public class minDistance {
public static int minDistance(String word1,String word2){
int len1 = word1.length();
int len2 = word2.length();
int[][] dp = new int[len1+1][len2+1];
for(int i = 1 ; i <= len1 ;i++){
dp[i][0] = i;
}
for(int i = 1 ; i <= len2;i++){
dp[0][i] = i;
}
for(int i = 1 ; i <= len1;i++){
for(int j = 1 ; j <= len2;j++){
if(word1.charAt(i-1) == word2.charAt(j-1)){
dp[i][j] = dp[i-1][j-1];
}else{
dp[i][j] = Math.min(dp[i-1][j]+1,Math.min(dp[i][j-1]+1,dp[i-1][j-1]+1));
}
}
}
return dp[len1][len2];
}
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String word1 = sc.nextLine();
String word2 = sc.nextLine();
System.out.println("结果是"+minDistance(word1,word2));
}
}