//最长公共子序列
#include<bits/stdc++.h>
using namespace std;
//设f[i][j]表示序列a[1....i]和b[1....j]的最长公共子序列长度
//现在考察末尾元素a[i]与b[j]是否再公共子序列中
//(1)若a[i]=b[j],则a[i]与b[j]在公共子序列中
//所以f[i][j]=f[i-1][j-1]+1
//(2)若a[i]!=b[j],且a[i]不在公共子序列中,则可去掉a[i]
//所以f[i][j]=f[i-1][j]
//(3)若a[i]!=b[j],且b[j]不在公共序列中,则可去掉b[j]
//所以f[i][j]=f[i][j-1]
//特殊情况:a[i]!=b[j]且a[i]、b[j]均不在公共序列中,这种情况可以看成是第二第三情况的任意一种
则有:
/*
边界条件:
f[0][j]=0;f[i][0]=0;
*/
//p数组是记录前驱的位置
for(int i=1;i<=m;i++)
{
for(int j=1;j<=n;j++)
{
if(a[i]==b[j])
{
f[i][j]=f[i-1][j-1]+1;
p[i][j]=1;//左上方
}
else if(f[i][j-1]>f[i-1][j])
{
f[i][j]=f[i][j-1];
p[i][j]=2;//左边
}
else
{
f[i][j]=f[i-1][j];
p[i][j]=3;//上边
}
}
}
cout<<f[m][n];
//接下来是利用前驱数组来找寻最长公共子序列究竟是谁
int i,j,k;
char s[200];
i=m;j=n;k=f[m][n];
while(i>0&&j>0)
{
if(p[i][j]==1)//左上方
{
s[k--]=a[i-1];
i--;
j--;
}
else if(p[i][j]==2)//左边
{
j--;
}
else//上边
{
i--;
}
}
for(int i=1;i<=f[m][n];i++)
{
cout<<s[i];
}
最长公共子序列
最新推荐文章于 2024-10-07 19:01:55 发布