关于 unordered_map 和 map
查看原帖
关于 unordered_map 和 map
232838
huangkx楼主2024/5/26 17:29

写了一个后缀自动机,一开始用的 unordered_map 存转移边,有一个点 TLE 了,然后改成 map 就对了。请问这是为什么啊?(我以前一直以为 unordered_map 比 map 快,只是不是有序的)

提交记录:

map:https://www.luogu.com.cn/record/160374810

unordered_map:https://www.luogu.com.cn/record/160374431

代码:

#include <bits/stdc++.h>
#define ll long long
using namespace std;
namespace IO
{
	int read()
	{
		int f = 1, x = 0;
		char c = getchar();
		while(c < '0' || c > '9'){
			if(c == '-') f = - 1;
			c = getchar();
		}
		while(c >= '0' && c <= '9'){
			x = x * 10 + c - '0';
			c = getchar();
		}
		return f * x;
	}
	void write(int x)
	{
		if(x < 0){
			putchar('-');
			x = - x;
		}
		if(x > 9) write(x / 10);
		putchar(x % 10 + '0');
	}
}
using namespace IO;
// Fast IO sometimes -> Slow IO
const int N = 1e5;
struct SAM{
	int ed, lst;
	ll sum;
	int len[2 * N - 1 + 1 + 1];
	int fa[2 * N - 1 + 1 + 1];
	map < int, int > ch[2 * N - 1 + 1 + 1]; // 用 unordered_map 会 TLE 一个点,用 map 可以 AC,不知道为什么。
	void Init()
	{
		ed = 1;
		lst = ed;
		sum = 0ll;
	}
	ll Insert(int c)
	{
		int p = lst, np = ++ ed;
		lst = np;
		len[np] = len[p] + 1;
		while(p && ! ch[p][c]){
			ch[p][c] = np;
			p = fa[p];
		}
		if(! p){
			fa[np] = 1;
			sum += 1ll * (len[np] - len[fa[np]]);
			return sum;
		}
		int q = ch[p][c];
		if(len[q] == len[p] + 1){
			fa[np] = q;
			sum += 1ll * (len[np] - len[fa[np]]);
			return sum;
		}
		int nq = ++ ed;
		len[nq] = len[p] + 1; //
		ch[nq] = ch[q];
		while(p && ch[p][c] == q){
			ch[p][c] = nq;
			p = fa[p];
		}
		fa[nq] = fa[q];
		sum += 1ll * (len[nq] - len[fa[nq]]);
		sum -= 1ll * (len[q] - len[fa[q]]);
		fa[q] = nq;
		sum += 1ll * (len[q] - len[fa[q]]);
		fa[np] = nq;
		sum += 1ll * (len[np] - len[fa[np]]);
		return sum;
	}
}sam;
void solve()
{
	int n = read();
	vector < int > a(n + 1);
	for(int i = 1; i <= n; i ++) a[i] = read();
	sam.Init();
	for(int i = 1; i <= n; i ++) printf("%lld\n", sam.Insert(a[i]));
}
signed main()
{
	int t = 1;
	while(t --) solve();
	return 0;
}
2024/5/26 17:29
加载中...