技巧性暴力解法,我觉得挺优美的。但是我一开始方向就错了,最后还是没搞出来,水平太差,当然没有我这个渣渣怎么承托出大佬的厉害。
因为两个子串不能重叠,所以他们一定会关于某个点对称。
枚举每一个对称点,设立两个变量往两头进行迭代,把两个迭代所指向的字母差异值进行累加。
当某次累加超过m时,那就记录这个答案,再把最先进入的字母去掉(也就是把他们的差异值减去),直到小于或等于m。
最后答案取最大值。
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<string>
using namespace std;
char str[5010];
int m,len,ans;
int spread(int x,int y)
{
int sum=0,mres=0,px=x,py=y;
while(x>=0&&y<=len-1&&px>=x)
{
sum+=abs(str[x]-str[y]);
if(sum>m)
{
mres=max(mres,px-x);
while(sum>m) sum-=abs(str[px--]-str[py++]);
}
x--,y++;
}
if(sum<=m) mres=max(mres,px-x);
return mres;
}
int main()
{
int T;
//freopen("fuck.txt","r",stdin);
scanf("%d",&T);
for(int Case=1;Case<=T;Case++)
{
scanf("%d",&m);
ans=0;
scanf("%s",str);
len=strlen(str);
for(int i=0;i<len;i++) ans=max(ans,spread(i-1,i+1));
for(int i=0;i<len;i++) ans=max(ans,spread(i,i+1));
printf("%d\n",ans);
}
return 0;
}