一、模板:
洛谷P3804
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<vector>
#define ll long long
#define llu unsigned ll
using namespace std;
const int maxn=1000100;
char str[maxn];
int x[maxn<<1],y[maxn<<1];
struct Sam
{
int last,cnt;
int nt[maxn<<1][26],fa[maxn<<1];
int len[maxn<<1],sum[maxn<<1];
void init(void)
{
last=1;
cnt=1;
fa[1]=0;
len[1]=0;
}
void _insert(int c)
{
int nowp=++cnt,p=last;
len[nowp]=len[last]+1;
while(p&&!nt[p][c]) nt[p][c]=nowp,p=fa[p];
if(!p) fa[nowp]=1;
else
{
int q=nt[p][c];
if(len[q]==len[p]+1) fa[nowp]=q;
else
{
int nowq=++cnt;
len[nowq]=len[p]+1;
memcpy(nt[nowq],nt[q],sizeof(nt[q]));
fa[nowq]=fa[q];
fa[nowp]=fa[q]=nowq;
while(p&&nt[p][c]==q) nt[p][c]=nowq,p=fa[p];
}
}
last=nowp;
sum[last]=1;
return ;
}
void _count(void)
{
memset(x,0,sizeof(x));
for(int i=1;i<=cnt;i++) x[len[i]]++;
for(int i=1;i<=cnt;i++) x[i]+=x[i-1];
for(int i=1;i<=cnt;i++) y[x[len[i]]--]=i;
for(int i=cnt;i>=1;i--)
sum[fa[y[i]]]+=sum[y[i]];
return ;
}
void creat(void)
{
int len=strlen(str);
init();
for(int i=0;i<len;i++)
_insert(str[i]-'a');
_count();
return ;
}
}sam;
int main(void)
{
scanf("%s",str);
sam.creat();
ll maxx=0;
for(int i=1;i<=sam.cnt;i++)
if(sam.sum[i]>1)
maxx=max((ll)sam.sum[i]*sam.len[i],maxx);
printf("%lld\n",maxx);
return 0;
}
二、string string string HDU - 6194 :
求出sum数组即可,判断是否与k相等,若相等,则节点i,代表的字符串都符合题意,求出节点i代表的字符串的个数即可。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<vector>
#define ll long long
#define llu unsigned ll
using namespace std;
const int maxn=100100;
char str[maxn];
int x[maxn<<1],y[maxn<<1];
struct Sam
{
int last,cnt;
int nt[maxn<<1][26],len[maxn<<1];
int fa[maxn<<1],sum[maxn<<1];
void init(int n)
{
last=1;
cnt=1;
fa[1]=0;
len[1]=0;
for(int i=0;i<=n;i++)
{
fa[i]=0;
len[i]=0;
sum[i]=0;
memset(nt[i],0,sizeof(nt[i]));
}
}
void _insert(int c)
{
int nowp=++cnt,p=last;
len[nowp]=len[last]+1;
while(p&&!nt[p][c]) nt[p][c]=nowp,p=fa[p];
if(!p) fa[nowp]=1;
else
{
int q=nt[p][c];
if(len[q]==len[p]+1) fa[nowp]=q;
else
{
int nowq=++cnt;
len[nowq]=len[p]+1;
memcpy(nt[nowq],nt[q],sizeof(nt[q]));
fa[nowq]=fa[q];
fa[nowp]=fa[q]=nowq;
while(p&&nt[p][c]==q) nt[p][c]=nowq,p=fa[p];
}
}
last=nowp,sum[last]=1;
return ;
}
void _count(void)
{
memset(x,0,sizeof(x));
for(int i=1;i<=cnt;i++) x[len[i]]++;
for(int i=1;i<=cnt;i++) x[i]+=x[i-1];
for(int i=1;i<=cnt;i++) y[x[len[i]]--]=i;
for(int i=cnt;i>=1;i--) sum[fa[y[i]]]+=sum[y[i]];
return ;
}
void creat(void)
{
int len=strlen(str);
init((len+5)*2);
for(int i=0;i<len;i++)
_insert(str[i]-'a'