这种题目是真正的好题。二维dp不难,难的是状压dp,记录左上的是细节,细节中的细节
class Solution {
public:
int longestCommonSubsequence(string text1, string text2) {
//字符串子序列也就是匹配问题就考虑二维dp或者滑动窗口
//滑动窗口不能确保顺序,还是得dp
//状态定义:dp[i][j]代表1的前i位和2的前j位最长的匹配长度
//状态转移:多种情况,如果相等,就继承前一位+1,如果不相等,就是继承i-1和j-1大的那个
//basecase:全是00
// vector<vector<int>> dp(text1.length()+1,vector<int>(text2.length()+1));
// for(int i = 1; i <= text1.length(); ++i){
// for(int j = 1; j <= text2.length(); ++j){
// if(text1[i-1] == text2[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[text1.length()][text2.length()];
//二维考虑状压,要考虑的是前和上和左上三个状态,左上会被修改,前就是要被修改过的,所以我们要来一个数记录左上,前就不用记了
vector<int> dp(text2.length()+1);
for(int i = 1; i <= text1.length(); ++i){
int zuoshang = 0;
for(int j = 1; j <= text2.length(); ++j){
int tmp = dp[j];//这个数就是左上,因为tmp赋值给zuoshang后,zuoshang下次用的到的时候就是算j+1的时候,我们记录的是上一层的前一个的,就是左上
if(text1[i-1] == text2[j-1]) dp[j] = zuoshang+1;
else dp[j] = max(dp[j],dp[j-1]);
zuoshang = tmp;
}
}
return dp[text2.length()];
}
};