您的位置:首页 > 其它

算法复习之::LCS最长公共子序列

2013-10-16 15:44 295 查看
算法思想:dp[i][j]记录到A[i],B[j]的位置是Lcs的最大长度,

    转移方程:I:dp[i][j]=max(dp[i-1][j],dp[i][j]) (i>1)

         II:dp[i][j]=max(dp[i][j-1],dp[i][j]) (j>1)

         III:dp[i][j]=max(dp[i][j],dp[i-1][j-1]+1) (A[i]==A[j],i>1,j>1)

    处理完后,再从dp[A.length][B.length]处开始回溯找出最大子序列。

代码:

  

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <cstdlib>
using namespace std;

char A[100],B[100];
int dp[110][110],cnt;
char ans[110];

void ini()
{
cnt=0;
scanf("%s",A);
scanf("%s",B);
memset(dp,0,sizeof(dp));
memset(ans,'\0',sizeof(ans));
}
void DP()
{
int a=strlen(A),b=strlen(B);
for(int i=0;i<a;i++)
for(int j=0;j<b;j++)
{
if(i>0) dp[i][j]=max(dp[i-1][j],dp[i][j]);
if(j>0) dp[i][j]=max(dp[i][j],dp[i][j-1]);
if(A[i]==B[j])
{
if(i==0 || j==0) dp[i][j]=max(dp[i][j],1);
else dp[i][j]=max(dp[i][j],dp[i-1][j-1]+1);
}
}
}
void dfs(int i,int j)
{
if(i==0 || j==0)
{
if(A[i]==B[j]) ans[cnt++]=A[i];
return;
}
if(A[i]==B[j] && dp[i][j]>dp[i-1][j-1] && dp[i][j]>dp[i-1][j] && dp[i][j]>dp[i][j-1])
{
ans[cnt++]=A[i];
dfs(i-1,j-1);
}
else
{
if(dp[i][j]==dp[i-1][j-1]) dfs(i-1,j-1);
else if(dp[i][j]==dp[i][j-1]) dfs(i,j-1);
else dfs(i-1,j);
}
}
int main()
{
ini();
DP();
dfs(strlen(A)-1,strlen(B)-1);
for(int i=alen-1;i>=0;i--) cout<<ans[i];
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: