没法用逆序做,只能用顺序做。因为这里涉及到3个状态量,即左,上,左上三个状态量,用temp变量保存左上角的变量。空间复杂度O(n+1)+1。
但是01背包问题却可以用逆序做,因为只涉及两个状态量:上面的和左上角的。
//LCS只用一个数组+一个prev变量的解法。其中backup变量可以省去 ,用curr[0]代替。数组长度取X和Y的长度的最小值。
#include <iostream>
#include <string>
using namespace std;
// Space optimized function to find length of Longest Common Subsequence
// of substring X[0..m-1] and Y[0..n-1]
int LCSLength(string X, string Y)
{
int m = X.length(), n = Y.length();
// allocate storage for one-dimensional array curr
int curr[n + 1], prev;
// fill the lookup table in bottom-up manner
for (int i = 0; i <= m; i++)
{
prev = curr[0];
for (int j = 0; j <= n; j++)
{
int backup = curr[j];
if (i == 0 || j == 0)
curr[j] = 0;
else
{
// if current character of X and Y matches
if (X[i - 1] == Y[j - 1])
curr[j] = prev + 1;
// else if current character of X and Y don't match
else
curr[j] = max(curr[j], curr[j - 1]);
}
prev = backup;
}
}
// LCS will be last entry in the lookup table
return curr[n];
}
// Longest Common Subsequence problem space optimized solution
int main()
{
string X = "XMJYAUZ", Y = "MZJAWXU";
// pass smaller string as second argument to LCSLength()
if (X.length() > Y.length())
cout << "The length of LCS is " << LCSLength(X, Y);
else
cout << "The length of LCS is " << LCSLength(Y, X);
return 0;
}
LCS的递归写法: