将字符串进行复制,后缀排序后,对sa[i]进行查找。若sa[i]<=len,则输出s[sa[i]+len-1]即可。
应该算是SA最裸的题了,不需要求height。
#include <bits/stdc++.h>
using namespace std;
const int N=2e6+5;
int n,m,len;
int sum[N],rk[N],rk2[N],tp[N],sa[N],height[N];
char s[N];
inline void qsort()
{
for (register int i=0; i<=m; ++i) sum[i]=0;
for (register int i=1; i<=n; ++i) sum[rk[i]]++;
for (register int i=1; i<=m; ++i) sum[i]+=sum[i-1];
for (register int i=n; i>=1; --i) sa[sum[rk[tp[i]]]]=tp[i],sum[rk[tp[i]]]--;
}
inline void SA()
{
m=130;
for (register int i=1; i<=n; ++i) rk[i]=s[i]-'0'+1,tp[i]=i;
qsort();
int p=0;
for (register int len=1; p<n; m=p,len<<=1)
{
p=0;
for (register int i=n-len+1; i<=n; ++i) tp[++p]=i;
for (register int i=1; i<=n; ++i) if (sa[i]>len) tp[++p]=sa[i]-len;
qsort();
memcpy(rk2,rk,sizeof(rk2));
p=1; rk[sa[1]]=p;
for (register int i=2; i<=n; ++i)
{
if (rk2[sa[i]]==rk2[sa[i-1]] && rk2[sa[i]+len]==rk2[sa[i-1]+len]) p=p; else p++;
rk[sa[i]]=p;
}
}
}
int main(){
scanf("%s",s+1);
len=strlen(s+1);
n=len<<1;
for (register int i=1; i<=len; ++i) s[i+len]=s[i];
SA();
for (register int i=1; i<=n; ++i) if (sa[i]<=len) putchar(s[sa[i]+len-1]);
return 0;
}