將字串進行復制,后綴排序后,對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) printf("%d ",sa[i]); puts("");
for (register int i=1; i<=n; ++i) if (sa[i]<=len) putchar(s[sa[i]+len-1]);
return 0;
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/92517.html
標籤:其他
