刚学SAM,MLE
查看原帖
刚学SAM,MLE
227824
JK_LOVER楼主2020/8/21 07:45

9个点超空间,怀疑是写挂了,但是开小后又RE了/kk。

#include<bits/stdc++.h>
using namespace std;
const int MAXLEN = 1000011;
struct SAM{
	struct Node{
		int len,link,si;
		int nxt[26];
	};
	Node st[MAXLEN << 1];
	int si,last;
	void init(){
		st[0].len = 0;
		st[0].link = -1;
		si++;
		last = 0;
	}
	void insert(int c){
		int cur = si++;
		st[cur].si = 1;
		st[cur].len = st[last].len + 1;
		int p = last;
		while(p != -1 && !st[p].nxt[c]){
			st[p].nxt[c] = cur;
			p = st[p].link;
		}
		if(p == -1) {
			st[cur].link = 0;
		}
		else 
		{
			int q = st[p].nxt[c];
			if(st[p].len + 1 == st[q].len)
			{
				st[cur].link = q;
			}
			else 
			{
				int clone = si++;
				st[clone].len = st[p].len + 1;
				for(int i = 0;i < 26;i++) st[clone].nxt[i] = st[q].nxt[i];
				st[clone].link = st[q].link;
				while(p != -1 && st[p].nxt[c] == q)
				{
					st[p].nxt[c] = clone;
					p = st[p].link;
				}
				st[q].link = st[cur].link = clone;
			}
		}
		last = cur;
	}
}sam;
const int N = 1000010;
int head[N],cnt,nxt[N<<2],to[N<<2];
void build(){
	for(int i = 1;i < sam.si;i++)
	{
		int x = sam.st[i].link,y = i;
		to[++cnt] = y;nxt[cnt] = head[x];head[x] = cnt;
	}
}
long long ans = 0;
void dfs(int u){
	for(int i = head[u];i;i = nxt[i]){
		dfs(to[i]);sam.st[u].si+=sam.st[to[i]].si;
	}
	if(sam.st[u].si^1) ans = max(ans,1LL * sam.st[u].si * sam.st[u].len);
}
char ch[N];
int main()
{
	scanf("%s",ch);int L = strlen(ch);
	sam.init();
	for(int i = 0;i < L;i++) sam.insert(ch[i]-'a');
	build();
	dfs(0);
	cout << ans << endl;
	return 0;
}
2020/8/21 07:45
加载中...