编辑距离
给你两个单词 word1 和 word2, 请返回将 word1 转换成 word2 所使用的最少操作数 。
你可以对一个单词进行如下三种操作:
插入一个字符
删除一个字符
替换一个字符
示例 1:
输入:word1 = “horse”, word2 = “ros”
输出:3
解释:
horse -> rorse (将 ‘h’ 替换为 ‘r’)
rorse -> rose (删除 ‘r’)
rose -> ros (删除 ‘e’)
示例 2:
输入:word1 = “intention”, word2 = “execution”
输出:5
解释:
intention -> inention (删除 ‘t’)
inention -> enention (将 ‘i’ 替换为 ‘e’)
enention -> exention (将 ‘n’ 替换为 ‘x’)
exention -> exection (将 ‘n’ 替换为 ‘c’)
exection -> execution (插入 ‘u’)
提示:
0 <= word1.length, word2.length <= 500
word1 和 word2 由小写英文字母组成
dp数组含义:dp[i][j] 字符串s1前i个与字符串s2前j个匹配所需要的最小操作数;
三种操作的递推公式:
已知dp[i][j]
删除:dp[i+1][j] = min(dp[i+1][j],dp[i][j]+1); //s1串向后扩一个
增加:dp[i][j+1] = min(dp[i][j+1],dp[i][j]+1); //s2串向后扩一个
替换:dp[i+1][j+1] = min(dp[i+1][j+1],dp[i][j]+(s1[i+1]==s2[j+1]?0:1); //s1、s2串同时向后扩一个并判断下一个位置上的字符是否相同
Code_1:
int f[550][550];
int minDistance(string s1, string s2) {
memset(f,127,sizeof(f));
f[0][0] = 0;
int n = s1.size();
int m = s2.size();
for(int i=1;i<=n;i++) f[i][0] = i;
for(int i=1;i<=m;i++) f[0][i] = i;
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
f[i][j] = min(f[i-1][j]+1,min(f[i][j-1]+1,f[i-1][j-1]+(s1[i-1]==s2[j-1]?0:1)));
return f[n][m];
}
Code_2:
int f[550][550];
int minDistance(string s1, string s2) {
memset(f,127,sizeof(f));
f[0][0] = 0;
int n = s1.size();
int m = s2.size();
for(int i=0;i<=n;i++) {
for(int j=0;j<=m;j++) {
if(i<n)f[i+1][j] = min(f[i][j]+1,f[i+1][j]);
if(j<m)f[i][j+1] = min(f[i][j]+1,f[i][j+1]);
if(i<n&&j<m) if(s1[i] == s2[j]) f[i+1][j+1] = min(f[i+1][j+1],f[i][j]);
if(i<n&&j<m) f[i+1][j+1] = min(f[i][j] + 1,f[i+1][j+1]);
}
}
return f[n][m];
}