合并回文子串
活动地址:https://ac.nowcoder.com/discuss/391086?type=101
思路
这是一道比较典型的区间dp题目,而区间dp很多时候都是小区间算好了结果,看能不能在此基础上更新大区间,这题也是如此。
这里我做了图解:
所以我们只需要把初始化工作做好,然后推下去就好。也就是把字符串长度为0和1的f[i,j][l,r] 设置成true就行了
代码
#include <iostream>
#include <algorithm>
#include <string>
#include <cstring>
#include <map>
#include <set>
#include <deque>
#include <queue>
#include <vector>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#define PI acos(-1)
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const ll maxn = 1e6+10;
double eps = 1e-8;
int T;
bool f[55][55][55][55];
char s1[55],s2[55];
int main(){
cin>>T;
while(T--){
memset(f, false,sizeof f);
int mx = 0;
scanf("%s %s",s1+1,s2+1);
int len1 = strlen(s1+1),len2 = strlen(s2+1);
for(int L1 = 0;L1<=len1;L1++){
for(int L2 = 0;L2<=len2;L2++){
for(int i = 1;i<=len1-L1+1;i++){
for(int l = 1;l<=len2-L2+1;l++){
int j = i+L1-1,r = l+L2-1;
bool &t = f[i][j][l][r]; //用引用方便些
if(L1+L2 <= 1) t = true; //初始化工作
else{//这里改变了一下,跟图片中倒着想一想就知道了
if(s1[i] == s1[j]) t |= f[i+1][j-1][l][r];
if(s2[l] == s2[r]) t |= f[i][j][l+1][r-1];
if(s1[i] == s2[r]) t |= f[i+1][j][l][r-1];
if(s1[j] == s2[l]) t |= f[i][j-1][l+1][r];
}
if(t) mx = max(mx,L1+L2);
}
}
}
}
printf("%d\n",mx);
}
return 0;
}
京公网安备 11010502036488号