多校6 HDU-6103 Kirinriki 双指针

来源:互联网 发布:苏宁易购淘宝旗舰店 编辑:程序博客网 时间:2024/05/17 01:36

原题链接:
HDU-6103

大意:
给一个串,求两个不重叠的长度均为 n 的子串 A , B,求A,B距离

disA,B=i=0n1|AiBn1i|

思路:
题目和样例都给了暗示,回文串。
可以发现两个子串一定存在一个对称中心,围绕对称中心往外做,双指针维护即可。找到大于 m 的就进行维护。

做的时候两条 for 语句写起来比较清晰,对称中心在空隙处一个,对称中心为数字一个。

#include <bits/stdc++.h>using namespace std;typedef long long ll;#define mem(s,t) memset(s,t,sizeof(s))#define D(v) cout<<#v<<" "<<v<<endl#define inf 0x3f3f3f3f//#define LOCALinline void read(int &x){    x=0;char p=getchar();    while(!(p<='9'&&p>='0'))p=getchar();    while(p<='9'&&p>='0')x*=10,x+=p-48,p=getchar();}const int MAXN=5000+10;char s[MAXN];int m;int main() {#ifdef LOCAL    freopen("1008.in","r",stdin);    freopen("out.txt","w",stdout);#endif    int t;    read(t);    while(t--){        mem(s,0);        read(m);        scanf("%s",s);        int len=strlen(s);        int ans=0;        int n=0;        for(int i=1;i<len;i++){//对称中心为数字之间空隙            for(int l=i-1,r=i+1,pr=r,pl=l,ret=0;r<len && l>=0;r++,l--){                ret+=abs(s[r]-s[l]);                while(ret>m && pr<=r){                    ret-=abs(s[pr++]-s[pl--]);                }                n=max(n,r-pr+1);            }        }        for(int i=1;i<len;i++){//对称中心为数字            for(int l=i-1,r=i,pr=r,pl=l,ret=0;r<len && l>=0;r++,l--){                ret+=abs(s[r]-s[l]);                while(ret>m && pr<=r){                    ret-=abs(s[pr++]-s[pl--]);                }                n=max(n,r-pr+1);            }        }        printf("%d\n",n);    }    return 0;}
原创粉丝点击