下面是一段自写代码的呈现,如果后期有不明白,自己查阅收藏博客
主要方法:画出表格图,列出递归公式
自写1:
#include
#include
void print(int i, int j, int s, char x[], char y[]);
int c[200][200]; //用c[i][j]记录X[i]与Y[j] 的LCS 的长度
int b[200][200]; //b[i][j]记录c[i][j]是通过哪一个子问题的值求得的,以决定搜索的方向
char f[200];
/*-----------------------分割线--------------------------------*/
/*取c[i-1][j]和c[i][j-1]的最大值,并记录c[i][j]是通过哪一个子问题的值求得的,以决定搜索的方向*/
int Max(int m, int n, int i, int j)//m=c[i-1][j],n=c[i][j-1]
{
if (m > n)
//请输入字符串X:ACDSXZBF
//请输入字符串Y:ACGHNBFZ
{
b[i][j] = -1;
return m;//返回大的c[i-1][j]
}
else
{
b[i][j] = 1;
return n;//如果c[i-1][j]<=c[i][j-1],返回c[i][j-1]
}
}
/*-----------------------分割线--------------------------------*/
int LCS(char x[], char y[])
{
int i, j;
int x_len, y_len;
x_len = strlen(x);
y_len = strlen(y);
for (i = 0; i < x_len+1; i++)//发现一个奇怪的问题这边第一排第一列不初始化居然也行
c[i][0] = 0;
for (j = 0; j < y_len + 1; j++)
c[0][j] = 0;
for (i = 1; i <= x_len; i++)
{
for (j = 1; j <= y_len; j++)
{
if (x[i - 1] == y[j - 1])
{
c[i][j] = c[i - 1][j - 1] + 1;
b[i][j] = 0;//画龙点睛之笔
}
else
{
c[i][j] = Max(c[i - 1][j], c[i][j - 1], i, j);
}
}
}
/*-------------------------分割线---------------------------------------*/
//打印X和Y的LCS
printf("X和Y的LCS是:");
print(x_len, y_len, c[x_len][y_len], x, y);
printf("%s", f);
printf("\n");
return c[x_len][y_len];
}
/*-----------------------分割线--------------------------------*/
/*递归打印LCS的元素内容*/
void print(int i, int j, int s, char x[], char y[]) //i.j两个字符串的长度,s公共子序列的长度,两个字符串 .这边就是根据后面倒推出公共子序列的。******
{
if (b[i][j] == 0)//这个地方是有有问题的 ,后续代码解决了这个问题
{
f[s - 1] = x[i - 1];
i--; j--; s--;//因为下一个递归的数就是b[i-1][j-1],公共子序列地长度也就跟着递归减1
print(i, j, s, x, y);
}
else if (b[i][j] == -1)
{
i--; //m = c[i - 1][j], n = c[i][j - 1],大于返回-1
print(i, j, s, x, y);
}
else if (b[i][j] == 1)
{
j--;
print(i, j, s, x, y);
}
}
/*------------------------------分割线----------------------------------------*/
void main()
{
char X[200], Y[200];
int i, j, s;
printf("请输入字符串X:");
scanf("%s", X);
while (strlen(X) > 200)
{
printf("您输入的字符串超过最大长度,请重新输入!");
scanf("%s", X);
}
printf("请输入字符串Y:");
scanf("%s", Y);
while (strlen(Y) > 200)
{
printf("您输入的字符串超过最大长度,请重新输入!");
scanf("%s", Y);
}
s = LCS(X, Y);
printf("X和Y的LCS: %d \n", s);
}
自写2:
//最大公共子序列的问题
#include
#include
#define MAXSIZE 200
int c[200][200];
int b[200][200];
char f[200];
void print(int i,int j,int s,char x[],char y[]);
int max(int m,int n,int i,int j)//c[i][j-1].c[i-1][j]
{
if(m>n)
{
b[i][j]=1;
return m;}
else
{
b[i][j]=-1;
return n;}
}
int LCS(char x[],char y[])
{
int i,j;
int m,n;
m=strlen(x);
n=strlen(y);
for(i=0;i