제출 #13454

#제출 시각아이디문제언어결과실행 시간메모리
13454ainta회문 (APIO14_palindrome)C++98
100 / 100
974 ms70816 KiB
#include<stdio.h> #include<algorithm> #define N_ 300010 #define N2_ 600010 #define SZ 524288 using namespace std; char p[N2_]; int LCP[N2_][20], SA[N2_], Num[N2_], po[N2_]; struct Arr{ int a, b; }Li[N2_]; int n, m, C[N2_], ord[N2_], ord2[N2_]; void Suffix_Array(){ int i, L = 1, M, cnt; for (i = 1; i <= m; i++){ Li[i].a = p[i], Li[i].b = 0; } while (1){ M = max(m, 256); for (i = 1; i <= m; i++)C[Li[i].b]++; for (i = 1; i <= M; i++)C[i] += C[i - 1]; for (i = 1; i <= m; i++)ord[C[Li[i].b]--] = i; for (i = 0; i <= M; i++)C[i] = 0; for (i = 1; i <= m; i++)C[Li[i].a]++; for (i = 1; i <= M; i++)C[i] += C[i - 1]; for (i = m; i >= 1; i--)ord2[C[Li[ord[i]].a]--] = ord[i]; for (i = 0; i <= M; i++)C[i] = 0; cnt = 0; for (i = 1; i <= m; i++){ if (i == 1 || Li[ord2[i]].a != Li[ord2[i - 1]].a || Li[ord2[i]].b != Li[ord2[i - 1]].b)cnt++; SA[ord2[i]] = cnt; } if (L >= m)break; for (i = 1; i <= m; i++){ Li[i].a = SA[i]; if (i + L > m)Li[i].b = 0; else Li[i].b = SA[i + L]; } L *= 2; } for (i = 1; i <= m; i++)Num[SA[i]] = i; } void Make_LCP(){ int i, L = 0, x, j; for (i = 1; i <= m; i++){ if (SA[i] == m)continue; if (L)L--; x = Num[SA[i] + 1]; while (p[i + L] == p[x + L])L++; LCP[SA[i]][0] = L; } for (i = 0; i < 19; i++){ for (j = 1; j <= m; j++){ if (j + (1 << i) <= m) LCP[j][i + 1] = min(LCP[j][i], LCP[j + (1 << i)][i]); } } } int get_LCP(int b, int e){ if (b>e)return get_LCP(e, b); int d = po[e - b]; return min(LCP[b][d], LCP[e - (1 << d)][d]); } int w[N2_], S[N_]; long long Res; void Do(int ck){ int i, L = 0, j, Sum; for (i = 1; i <= m + 1; i++){ Sum = 0; while (L > LCP[i - 1][0]){ Sum += S[L]; S[L] = 0; Res = max(Res, (long long)Sum * (L * 2 - ck)); L--; } if (i == m + 1)break; S[L] += Sum; L = max(L, w[i]); S[w[i]]++; } } int main(){ int i; scanf("%s", p + 1); for (i = 1; p[i]; i++); n = i - 1; m = n + n + 1; p[n + 1] = ' '; for (i = 1; i <= n; i++)p[m + 1 - i] = p[i]; Suffix_Array(); Make_LCP(); for (i = 1; i <= m; i++){ po[i] = po[i - 1]; if ((1 << (po[i] + 1)) == i)po[i]++; } for (i = 1; i <= n; i++)w[SA[i]] = get_LCP(SA[i], SA[m + 1 - i]); Do(1); w[SA[1]] = 0; for (i = 2; i <= n; i++)w[SA[i]] = get_LCP(SA[i], SA[m + 2 - i]); Do(0); printf("%lld\n", Res); }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...