本地过了样例 在线IDE RE
#include<bits/stdc++.h>
using namespace std;
const int N=1e6+15;
int sa[N];//排名为i的后缀的起始位置
int rank1[N];//第i个后缀的排名
int tp[N];//用于存储第2关键字的排名
int tax[N];//上一轮后缀i的排名
char s1[N];//原始字符串
int height[N];
int n,m;
int len;
int l[N],r[N];
int color[N],cnt[N];
int q[N];
int nw=0;
void Qsort()
{
for(int i=0;i<=m;i++)
{
tax[i]=0;
}
for(int i=1;i<=n;i++)
{
tax[rank1[i]]++;
}
for(int i=1;i<=m;i++)
{
tax[i]+=tax[i-1];
}
for(int i=n;i>=1;i--)
{
sa[tax[rank1[tp[i]]]--]=tp[i];
}
}
void get_height()
{
int j;
int k = 0;
for(int i = 1; i <= n; i++)
{
if(k) k--;
int j = sa[rank1[i] - 1];
while(s1[i + k] == s1[j + k])
{
k++;
}
height[rank1[i]] = k;
}
}
void get_SA()
{
m=128;
for(int i=1;i<=n;i++)
{
rank1[i]=s1[i]-'0'+1;
tp[i]=i;
}
Qsort();
for(int w=1,p=0;p<n;w<<=1,m=p)
{
p=0;
for(int i=1;i<=w;i++)
{
tp[++p]=n-w+i;
}
for(int i=1;i<=n;i++)
{
if(sa[i]>w)
{
tp[++p]=sa[i]-w;
}
}
Qsort();
swap(rank1,tp);
rank1[sa[1]]=p=1;
for(int i=2;i<=n;i++)
{
rank1[sa[i]]=(tp[sa[i-1]]==tp[sa[i]] && tp[sa[i-1]+w] == tp[sa[i]+w]) ? p : ++p;
}
}
return;
}
void build_color()
{
for(int i=1;i<=len;i++)
{
for(int j=l[i];j<=r[i];j++)
{
color[rank1[j]] = i;
}
//cout<<l[i]<<" "<<r[i]<<endl;
}
}
void add(int x)
{
if(color[x] == 0)
{
return;
}
++cnt[color[x]];
if(cnt[color[x]] == 1)
{
++nw;
}
}
void del(int x)
{
if(color[x] == 0)
{
return;
}
--cnt[color[x]];
if(cnt[color[x]] == 0)
{
--nw;
}
}
int main()
{
cin>>len;
int idx=0;
// for(int i=1;i<=len;i++)
// {
// string c;
// l[i]=idx+1;
// cin>>c;
// for(int j=0;j<c.size();j++)
// {
// s1[++idx]=c[j];
// }
// r[i]=idx;
// s1[++idx]=i+'0';
// }
// n=strlen(s1+1);
for (int i = 1; i <= len; ++i)
{
l[i] = n + 1;
scanf("%s", s1 + n + 1);
n += strlen(s1 + n + 1);
r[i] = n;
s1[++n] = i + '0';
}
//cout<<n<<endl;
if(len==1)
{
cout<<strlen(s1+1);
return 0;
}
get_SA();
get_height();
// for(int i=1;i<=n;i++)
// {
// cout<<sa[i]-1<<" ";
// }
// cout<<endl;
// for(int i=1;i<=n;i++)
// {
// cout<<height[i]<<" ";
// }
// cout<<endl;
int ans=0;
build_color();
add(1);
// for(int i=1;i<=n;i++)
// {
// cout<<color[i]<<" ";
// }
// cout<<endl;
int head,tail,l1=1;
for(int i=2;i<=n;++i)
{
while(head<tail && height[q[tail]]>=height[i])
{
--tail;
}
q[++tail]=i;
add(i);
if(nw==len)
{
while(nw==len && l1<i)
{
del(l1++);
}
add(--l1);
}
while(head<tail && q[head]<=l1)
{
++head;
}
if(nw==len)
{
ans=max(ans,height[q[head]]);
}
cout<<1<<endl;
}
cout<<ans;
return 0;
}