[BZOJ 3676] [Apio2014] echo string, bzoj3676
3676: [Apio2014] Reply string
Time Limit: 20 Sec Memory Limit: 128 MB
Submit: 646 Solved: 219
[Submit] [Status] [Discuss]
Description
Consider a string s that only contains lowercase Latin letters. We define the output of a substring t of s.
The present value is the number of occurrences of t in s multiplied by the length of t. Please find the most
Large value.
Input
Enter only one line, which is a non-empty string s that only contains lowercase letters (a-z.
Output
Output an integer that indicates the maximum occurrence value of the input string.
Sample Input
[Example input l]
Abacaba
[Example input 2]
Www
Sample Output
[Sample output l]
7
[Sample output 2]
4
HINT
A string is a back-to-text string. If it is read from left to right, it is identical to read from right to left.
In the first example, there are seven input strings: a, B, c, aba, aca, bacab, and abacaba:
● A appears four times, and its appearance value is = 4
● B appears twice, and its appearance value is = 2
● C appears once, and its appearance value is l: 1: l = l
● Aba appears twice, and its appearance value is = 6
● Aca appears once, and its appearance value is 1 = 3
● Once bacab appears, its appearance value is = 5
● Abacaba appears once, and its appearance value is = 7
Therefore, the maximum return substring value is 7.
[Data scale and score]
The data must be 1 ≤ string length ≤ 300000.
Manacher + suffix array ~
You can know the process of calculating the length of the input string based on manacher. The length is N Only N Different types of input strings.
(Because only when maxid grows, it will generate different strings)
We only need O (n) The number of occurrences of each string.
Use the suffix array + binary to calculate the number of occurrences.
#include <iostream>#include <cstdio>#include <cstring>#include <cmath>#include <algorithm>#include <cstdlib>#define M 600010#define LL long longusing namespace std;int n,wa[M],sa[M],he[M],rk[M],f[M/2][20],c[M],wb[M],a[M],b[M];int wv[M],p[M];char s[M];int cmp(int *r,int a,int b,int l){ return r[a]==r[b]&&r[a+l]==r[b+l];}void da(int *r,int *sa,int n,int m){ int *x=wa,*y=wb,*t,i,j,p; for (i=0;i<m;i++) c[i]=0; for (i=0;i<n;i++) c[x[i]=r[i]]++; for (i=1;i<=m;i++) c[i]+=c[i-1]; for (i=n-1;i>=0;i--) sa[--c[x[i]]]=i; for (j=1,p=1;p<n;j*=2,m=p) { for (p=0,i=n-j;i<n;i++) y[p++]=i; for (i=0;i<n;i++) if (sa[i]>=j) y[p++]=sa[i]-j; for (i=0;i<n;i++) wv[i]=x[y[i]]; for (i=0;i<m;i++) c[i]=0; for (i=0;i<n;i++) c[wv[i]]++; for (i=1;i<m;i++) c[i]+=c[i-1]; for (i=n-1;i>=0;i--) sa[--c[wv[i]]]=y[i]; for (t=x,x=y,y=t,p=1,x[sa[0]]=0,i=1;i<n;i++) x[sa[i]]=cmp(y,sa[i-1],sa[i],j)?p-1:p++; }}void Calheight(int *r,int *sa,int n){ for (int i=1;i<=n;i++) rk[sa[i]]=i; int k=0; for (int i=0;i<n;i++) { if (k) k--; int j=sa[rk[i]-1]; while (r[i+k]==r[j+k]) k++; he[rk[i]]=k; }}void Getst(){ for (int i=0;i<=n;i++) f[i][0]=he[i]; for (int j=1;(1<<j)<=n;j++) for (int i=0;i+(1<<j)-1<=n;i++) f[i][j]=min(f[i][j-1],f[i+(1<<(j-1))][j-1]);}int Calmin(int l,int r){ int len=r-l+1,k=0,now=1; for (int i=0;i<=20;i++) { if (now*2>=len) { k=i; break; } now<<=1; } return min(f[l][k],f[r-(1<<k)+1][k]);}int Query(int x,int k){ int l,r,ql,qr; if (he[x+1]<k) qr=x; else { l=x+1,r=n; while (l<=r) { int mid=(l+r)>>1; if (Calmin(x+1,mid)>=k) qr=mid,l=mid+1; else r=mid-1; } } if (he[x]<k) ql=x; else { l=1,r=x-1; while (l<=r) { int mid=(l+r)>>1; if (Calmin(mid+1,x)>=k) ql=mid,r=mid-1; else l=mid+1; } } return qr-ql+1;}int main(){ scanf("%s",s); n=strlen(s); for (int i=0;i<n;i++) a[i]=s[i]-'a'+1; a[n]=0; da(a,sa,n+1,27); Calheight(a,sa,n); Getst(); for (int i=0;i<n;i++) b[i<<1]=a[i]; LL ans=1; int id=0,maxid=-1; for (int i=0;i<(n<<1);i++) { if (maxid>i) p[i]=min(maxid-i,p[2*id-i]); else p[i]=1; while (i-p[i]>=0&&b[i+p[i]]==b[i-p[i]]) p[i]++; p[i]--; if (p[i]+i>maxid) { for (int j=maxid+1;j<=p[i]+i;j++) if ((j&1)==0) { int f=i*2-j; int len=(j-f+2)/2; ans=max(ans,1LL*len*Query(rk[f>>1],len)); } maxid=p[i]+i,id=i; } } cout<<ans<<endl; return 0;}