您的位置:首页 > 其它

多校6 HDU-6103 Kirinriki 双指针

2017-08-11 16:01 405 查看
原题链接:

HDU-6103

大意:

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

disA,B=∑i=0n−1|Ai−Bn−1−i|

思路:

题目和样例都给了暗示,回文串。

可以发现两个子串一定存在一个对称中心,围绕对称中心往外做,双指针维护即可。找到大于 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 LOCAL
inline 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;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  双指针 多校