Catching Cheaters CodeForces - 1446B

原题链接
考察:线性DP
错误思路:
  求出最长公共子序列再dfs回溯枚举长度.
错误原因:
  不一定只存在一个最长公共子序列.比如样例2.
正确思路:
  是dp(...),定义 f[i][j] 为以1~i,1~j构成的最长公共子序列的最大S值,且A子串以i结尾,b子串由j结尾.这里其实类似最大连续子段和的问题,我们不确定结果是以什么结尾,所以每个取max
If a[i]==b[j] f[i][j] = f[i-1][j-1]+4-2.
else f[i][j] = max(f[i-1][j],f[i][j-1])-1.

Code

#include <iostream>
#include <cstring>
using namespace std;
typedef long long LL;
const int N = 5010;
char a[N],b[N];
int f[N][N],m,n;
int main() 
{
	scanf("%d%d",&n,&m);
	scanf("%s%s",a+1,b+1);
	int res = 0;
	for(int i=1;i<=n;i++)
	 for(int j=1;j<=m;j++)
	 {
	 	if(a[i]==b[j]) f[i][j] = max(f[i-1][j-1]+2,f[i][j]);
	 	else f[i][j] = max(f[i-1][j],f[i][j-1])-1;
	 	f[i][j] = max(f[i][j],0);
	 	res = max(f[i][j],res);
	 }
	printf("%d\n",res);
	return 0;
}
posted @ 2021-06-06 09:23  acmloser  阅读(40)  评论(0编辑  收藏  举报