杭电3068——manacher(马拉车)最长回文串
原题传送门
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
using namespace std;
const int maxn = 300000;
char a[maxn], b[maxn];
int p[maxn];
int len_a, len_b;
void init() {
len_b = 2 * len_a + 2;
b[0] = '$';
b[1] = '#';
for (int i = 0; i < len_a; i++) {
b[2 * i + 2] = a[i];
b[2 * i + 3] = '#';
}
b[len_b] = '*';
}
void manacher() {
int pos = 0, mx = 0;
for (int i = 0; i < len_b; i++) {
if (mx > i)
p[i] = min(p[2 * pos - i], mx - i);
else
p[i] = 1;
while (b[i - p[i]] == b[i + p[i]])
p[i]++;
if (i + p[i] > mx) {
mx = i + p[i];
pos = i;
}
}
}
int main() {
ios::sync_with_stdio(false);
while (cin>>a) {
len_a = (int)strlen(a);
init();
manacher();
int ans = 0;
for (int i = 0; i < len_b; i++)
ans = max(p[i], ans);
cout << ans - 1 << endl;
}
return 0;
}