最长公共子序列之回溯

大概写一下 有时间再完善

1.用vir[][][]数组记录此次选择的上一个选择位置

2.数组cc[][]记录此次选择的最长公共子序列的最后一位的在a字符串的下标  cc[i][j]=0表示从上个位置到此次位置没有更新更好的


回溯  数组cc里面存的就是最长公共子序列






/*
最长公共子序列之回溯
*/
#include<cstdio>
#include<iostream>
#include<cstring>
#include<string>
#include<cmath>
#include<algorithm>
#include<cstdlib>
#define N 1300
#define INF 0x3f3f3f3f
using namespace std;
int vir[N][N][2],cc[N][N];
int dp[N][N];
int lcs(char* a,char* b,int la,int lb)
{
    memset(dp,0,sizeof(dp));
    memset(cc,0,sizeof(cc));
    for(int i=1; i<=la; i++)
        for(int j=1; j<=lb; j++)
        {
            if(a[i]==b[j])
            {
                dp[i][j]=dp[i-1][j-1]+1;
                vir[i][j][0]=i-1;
                vir[i][j][1]=j-1;
                cc[i][j]=i;
            }
            else
            {
                cc[i][j]=0;
                if(dp[i-1][j]>=dp[i][j-1])
                {
                    dp[i][j]=dp[i-1][j];
                    vir[i][j][0]=i-1;
                    vir[i][j][1]=j;
                }
                else
                {
                    dp[i][j]=dp[i][j-1];
                    vir[i][j][0]=i;
                    vir[i][j][1]=j-1;
                }
            }
        }
    return dp[la][lb];
}
int main()
{
    char s1[N],s2[N];
    int res[N],la,len1,len2,ii,jj;
    int t=5;
    while(t--)
    {
        scanf("%s %s",s1+1,s2+1);
        len1=strlen(s1+1);
        len2=strlen(s2+1);
        lcs(s1,s2,len1,len2);
        la=0;
        ii=len1;
        jj=len2;
        int mi,mj;
        while(ii&&jj)
        {
            if(cc[ii][jj])
            {
                res[la++]=cc[ii][jj];
            }
            mi=ii;//回溯
            mj=jj;
            ii=vir[mi][mj][0];
            jj=vir[mi][mj][1];
        }
//        for(int i=0;i<la;i++)
//            printf("%d ",res[i]);
        puts("--------");
        printf("the most len ss:");
        for(int i=la-1;i>=0;i--)
            printf("%c",s1[res[i]]);
        puts("");


    }
}

猜你喜欢

转载自blog.csdn.net/dch19990825/article/details/79726290