583. 两个字符串的删除操作
题目描述:
给定两个单词 word1 和 word2,找到使得 word1 和 word2 相同所需的最小步数,每步可以删除任意一个字符串中的一个字符。
示例 1:
输入:"sea", "eat"
输出:2
解释:第一步将"sea"变为"ea",第二步将"eat"变为"ea"
说明:
- 给定单词的长度不超过500。
- 给定单词中的字符只含有小写字母。
算法:
可以通过间接求两个单词的最长公共子序列求解,比如示例中"sea"和"eat"的最长公共子序列是"ea",长度为2。
不难看出 answer = lengthOfWord1 - 2 + lengthOfWord2 - 2
LCS问题可以使用动态规划求解,具体的实现思路强烈推荐学习《算法导论(第三版)》中15.4一讲。
代码:
1 class Solution { 2 public: 3 //当值从对角线传过来时,b的值为1;当值从左边传过来时,b的值为0;当值从上穿过来时,b的值为2 4 //b[N][N]是记录值的传导方向,在这一题中无关紧要,可加可不加 5 int c[N][N] = {0}, b[N][N] = {0}; 6 7 // string backstr = ""; 8 int LCS(string &X, string &Y) 9 { 10 int lenX = X.size(); 11 int lenY = Y.size(); 12 for(int i = 0; i <= lenX; i++) 13 { 14 for(int j = 0; j <= lenY; j++) 15 { 16 if(i == 0 || j == 0) 17 c[i][j] = 0; 18 else 19 { 20 if(X[i-1] == Y[j-1]) 21 { 22 c[i][j] = c[i-1][j-1] + 1; 23 b[i][j] = 1; 24 } 25 else 26 { 27 if(c[i - 1][j] > c[i][j - 1]) 28 { 29 c[i][j] = c[i - 1][j]; 30 b[i][j] = 2; 31 } 32 33 else if(c[i - 1][j] < c[i][j - 1]) 34 { 35 c[i][j] = c[i][j - 1]; 36 b[i][j] = 0; 37 } 38 39 else 40 { //当相等时,默认从上传过来 41 c[i][j] = c[i - 1][j]; 42 b[i][j] = 2; 43 } 44 } 45 } 46 } 47 } 48 49 return lenX + lenY - 2 * c[lenX][lenY]; 50 } 51 };