https://vjudge.net/contest/345347#overview
题解:
A、B、C:
KMP的模板题,注意数据范围;
D:
利用Next数组求循环节,可以注意到最大循环节的长度len为n - Next[n];
如果n % len为0,则不用添加额外的字符,否则需要添加len - n % len 个字符
具体代码与思路描述有差异,这与打法有关。
E:
Manacher的变形,只需要在更新回文串长度的时候保证单调即可。
F:
Manacher,字母转换的时候,把26个字母看作一个环,顺序转换即可。
G:
Manacher模板。
代码:
D:
#include<iostream>
#include<cstring>
#include<cstdio>
#include<algorithm>
using namespace std;
const int MAXN = 100000 + 22;
int Next[MAXN];
int T,n;
char s[MAXN];
void init_Next(){
memset(Next,0,sizeof(Next));
int j = -1;
Next[0] = -1;
for(int i = 1;i < n;i ++){
while(s[i] != s[j + 1] && j != -1) j = Next[j];
if(s[i] == s[j + 1]) j ++;
Next[i] = j;
}
return;
}
void solve(){
scanf("%s",s);
n = strlen(s);
init_Next();
int len = n - (Next[n - 1] + 1);
if(n % len == 0 && n != len) cout << "0" << endl;
else cout << len - n % len << endl;
return;
}
int main(){
cin >> T;
while(T --)
solve();
return 0;
}
F:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int MAXN = 330010;
char s[MAXN],str[MAXN];
char f;
int n,len,mr,mid,l,r,pos;
int p[MAXN];
void init(){
memset(str,0,sizeof(str));
int j = 0;
str[j ++] = '$';
for(int i = 0;i < n;i ++){
str[j ++] = '#';
str[j ++] = s[i];
}
str[j ++] = '#';
len = j;
return;
}
int Manacher(){
int ans;
p[0] = pos = l = r = mr = mid = ans = 0;
for(int i = 1;i < len;i ++){
if(i < mr) p[i] = min(p[(mid << 1) - i],mr - i);
else p[i] = 1;
while(str[i - p[i]] == str[i + p[i]]) p[i] ++;
if(i + p[i] > mr){
mr = i + p[i];
if(ans < p[i]){
ans = p[i];
pos = i;
}
mid = i;
}
}
return ans - 1;
}
void solve(){
n = strlen(s);
int t = 'a' - 'A';
int num = 'A' + 26 - (f - t);
for(int i = 0;i < n;i ++){
s[i] -= t;
s[i] = (s[i] + num);
if(s[i] > 'Z')
s[i] -= 26;
s[i] += t;
}
init();
int ans = Manacher();
if(ans >= 2){
if(str[pos] == '#')
pos = pos / 2,l = pos - ans / 2,r = pos + ans / 2 - 1;
else
pos = pos / 2 - 1,l = pos - ans / 2,r = pos + ans / 2;
printf("%d %d\n",l,r);
for(int i = l;i <= r;i ++) printf("%c",s[i]);
printf("\n");
}
else printf("No solution!\n");
getchar();
return;
}
int main(){
while(~scanf("%c%s",&f,s))
solve();
return 0;
}