lcs(最长公共子序列),dp
lcs(最长公共子序列)
求两个序列的lcs的长度,子序列可不连续
dp[i][j]=dp[i-1][j-1]+1(a[i]==b[i])
dp[i][j]=max(dp[i-1][j],dp[i][j-1])(a[i]!=b[i])
memset(dp,0,sizeof(dp)); for(int i=1;i<=n1;i++){ for(int j=1;j<=n2;j++){ if(a[i]==b[j]) dp[i][j]=dp[i-1][j-1]+1; else dp[i][j]=max(dp[i-1][j],dp[i][j-1]); } } cout<<dp[n1][n2]<<endl;
以下是滚动数组的版本
#include<iostream> #include<cstdio> #include<cstdlib> #include<cstring> #include<algorithm> using namespace std; const int maxn=1000100; char s[maxn],t[maxn]; int dp[2][maxn]; int main() { while(scanf("%s%s",s,t)!=EOF){ int ls=strlen(s),lt=strlen(t); memset(dp,0,sizeof(dp)); char *ss=s-1,*tt=t-1; memset(dp,0,sizeof(dp)); for(int i=1;i<=ls;i++){ for(int j=1;j<=lt;j++){ if(ss[i]==tt[j]) dp[i%2][j]=dp[(i+1)%2][j-1]+1; else dp[i%2][j]=max(dp[(i+1)%2][j],dp[i%2][j-1]); } } printf("%d\n",dp[ls%2][lt]); } return 0; }
当两个序列中其中一个为升序时且长度相等时,这两个序列的lcs即为另一个序列的lis (hduoj1025)
没有AC不了的题,只有不努力的ACMER!