递归方法
方法1
- 只过了17/43个样例,因为递归的过程中重复计算了很多子问题
- dp[i][j]指str1[1…i] str2[1…i]间的LCS 最大公共子序列
class Solution {
public:
int longestCommonSubsequence(string text1, string text2) {
int i=text1.length()-1, j=text2.length()-1;
str1=text1;
str2=text2;
return dp(i,j);
}
private:
int dp(int i, int j){
if(i==-1 || j==-1) return 0;
if(str1.at(i) == str2.at(j))
return dp(i-1, j-1)+1;
else
return max(dp(i-1,j), dp(i,j-1));
}
string str1, str2;
};
方法2
class Solution {
public:
int longestCommonSubsequence(string text1, string text2) {
int i=text1.length()-1, j=text2.length()-1;
str1=text1;
str2=text2;
memset(memo, 0, sizeof(memo));
return dp(i,j);
}
private:
string str1, str2;
int memo[1005][1005];
int dp(int i, int j){
if(i==-1 || j==-1) return 0;
if(memo[i][j]) return memo[i][j];
if(str1.at(i) == str2.at(j)){
memo[i][j] = dp(i-1, j-1)+1;
}
else{
memo[i][j] =max(dp(i-1,j), dp(i,j-1));
}
return memo[i][j];
}
};
动态规划
- 刻意进行了错位处理,1->ii, 1->jj 为的是避免dp[-1][-1]出现
class Solution {
public:
int longestCommonSubsequence(string text1, string text2) {
int ii=text1.length(), jj=text2.length();
vector<vector<int>> dp(ii+1, vector<int>(jj+1,0));
for(int i=1; i<=ii; i++)
for(int j=1; j<=jj; j++){
if(text1.at(i-1)==text2.at(j-1))
dp[i][j] = dp[i-1][j-1]+1;
else
dp[i][j] = max(dp[i-1][j], dp[i][j-1]);
}
return dp[ii][jj];
}
};