mxqz SAM,对着题解看了好久不知道哪错了
查看原帖
mxqz SAM,对着题解看了好久不知道哪错了
363036
chlchl楼主2022/7/28 22:34
#include<bits/stdc++.h> 
#define ll long long
using namespace std;

const int N = 1e6 + 10;
char s[N];
int n, lst = 1, tot = 1;//记得初始化这俩玩意儿 
ll ans;
struct SAM{
	int len, fa, sz, son[30];
	SAM(){memset(son, 0, sizeof(son)), fa = len = sz = 0;}
} sam[N];
vector<int> g[N];

void insert(int c){
	int u = lst, v = ++tot;
	lst = tot, sam[v].len = sam[u].len + 1, sam[tot].sz = 1;
	while(u && !sam[u].son[c])	sam[u].son[c] = v, u = sam[u].fa;
	if(!u)	sam[v].fa = 1;
	else{
		int p = sam[u].son[c];
		if(sam[p].len == sam[u].len + 1)	sam[v].fa = p;
		else{
			int q = ++tot;
			sam[q] = sam[p], sam[q].len = sam[u].len + 1;
			sam[p].fa = sam[v].fa = q;
			for(;u&&sam[u].son[c]==p;u=sam[u].fa)	sam[u].son[c] = q;
		}
	}
}

void dfs(int u){
	for(int v: g[u]){
		dfs(v);
		sam[u].sz += sam[v].sz;//统计sz,即出现次数 
	}
	if(sam[u].sz != 1)	ans = max(ans, (ll)sam[u].sz * sam[u].len);//更新答案 
}

int main(){
	scanf("%s", s);
	n = strlen(s);
	for(int i=0;i<n;i++)	insert(s[i] - 'a');
	for(int i=2;i<=tot;i++)	g[sam[i].fa].push_back(i);//建边,准备树形 DP 
	dfs(1);
	return printf("%lld\n", ans), 0;
}
2022/7/28 22:34
加载中...