QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#276349#7188. Aho-Corasick AutomatonPetroTarnavskyi#WA 3ms26304kbC++173.1kb2023-12-05 20:14:582023-12-05 20:14:58

Judging History

你现在查看的是最新测评结果

  • [2023-12-05 20:14:58]
  • 评测
  • 测评结果:WA
  • 用时:3ms
  • 内存:26304kb
  • [2023-12-05 20:14:58]
  • 提交

answer

#include <bits/stdc++.h>
using namespace std;

#define FOR(i, a, b) for(int i = (a); i < (b); i++)
#define RFOR(i, b, a) for(int i = (b) - 1; i >= (a); i--)
#define SZ(a) (int)a.size()
#define ALL(a) a.begin(), a.end()
#define PB push_back
#define MP make_pair
#define F first
#define S second

typedef long long LL;
typedef vector<int> VI;
typedef pair<int, int> PII;
typedef double db;

const LL mod1 = 1'000'000'007;
const LL mod2 = 1'000'000'009;
const LL mod = mod1 * mod2;

LL add(LL a, LL b)
{
	return a + b < mod ? a + b : a + b - mod;
}
LL sub(LL a, LL b)
{
	return a - b >= 0 ? a - b : a - b + mod;
}
LL mult(LL a, LL b)
{
	return (__int128)a * b % mod;
}

const int N = 200'447;
const int LOG = 18;
VI vec[N];
LL hs[N];
int h[N];
int up[LOG][N];

struct Node
{
	int p;
	int c;
	unordered_map<int, int> g;
	unordered_map<int, int> nxt;
	int link;
	
	void init()
	{
		c = -1;
		p = -1;
		link = -1;
	}
};

struct AC
{
	vector<Node> a;
	int sz;
	void init(int n)
	{
		a.resize(n);
		a[0].init();
		sz = 1;
	}
	int go(int v, int c)
	{
		if (a[v].g.count(c) == 1)
			return a[v].g[c];
			
		if (a[v].nxt.count(c) == 1)
			a[v].g[c] = a[v].nxt[c];
		else if (v != 0)
			a[v].g[c] = go(getLink(v), c);
		else
			a[v].g[c] = 0;
			
		return a[v].g[c];
	}
	int getLink(int v)
	{
		if (a[v].link != -1)
			return a[v].link;
		if (v == 0 || a[v].p == 0)
			return 0;
		return a[v].link=go(getLink(a[v].p), a[v].c);
	}
} ac;

const int MAGIC = 777;
int x = 7474747;
LL pw[N];

void dfs(int v, int c, int H)
{
	h[v] = H;
	hs[v] = add(mult(hs[up[0][v]], x), c);
	FOR (i, 1, LOG)
	{
		up[i][v] = up[i - 1][up[i - 1][v]];
	}
	for (auto [C, to] : ac.a[v].nxt)
	{
		dfs(to, C, H + 1);
	}
}

int f(int v, int c)
{
	int ans = 0;
	for (auto u : vec[c])
	{
		if (h[u] >= h[v])
			continue;
		int p = v;
		RFOR (i, LOG, 0)
		{
			if (h[v] - h[up[i][p]] <= h[u])
				p = up[i][p];
		}
		assert(p != 0);
		p = up[0][p];
		LL hsh = sub(hs[v], mult(hs[p], pw[h[u]]));
		if (hsh == hs[u] && h[u] > h[ans])
		{
			ans = u;
			break;
		}
	}
	ac.a[v].link = ans;
	return ans;
}

int main()
{
	ios::sync_with_stdio(0); 
	cin.tie(0);
	cout << fixed << setprecision(15);
	
	pw[0] = 1;
	FOR (i, 1, N)
		pw[i] = mult(pw[i - 1], x);
	
	int n;
	cin >> n;
	
	VI cnt(n);
	VI idx(n);
	iota(ALL(idx), 0);
	
	
	ac.init(n + 1);
	FOR(i, 0, n + 1)
		ac.a[i].init();
	
	VI p(n), c(n);
	FOR(i, 0, n)
		cin >> p[i];
	FOR(i, 0, n)
	{
		cin >> c[i];
		c[i]--;
		cnt[c[i]]++;
	}
	sort(ALL(idx), [&](int i, int j)
	{
		return cnt[i] > cnt[j];
	});
	VI a(n);
	FOR (i, 0, n)
		a[idx[i]] = i;
	
	FOR(i, 0, n)
	{
		ac.a[p[i]].nxt[c[i]] = i + 1;
		up[0][i + 1] = p[i];
		ac.a[i + 1].p = p[i];
		ac.a[i + 1].c = c[i];
		if (cnt[c[i]] < MAGIC)
			vec[c[i]].PB(i + 1);
	}
	FOR (i, 0, n)
	{
		sort(ALL(vec[i]), [&](int u, int v)
		{
			return h[u] > h[v];
		});
	}
	dfs(0, 0, 0);
	
	FOR(i, 1, n + 1)
	{
		if(i > 1)
			cout << " ";
		if (cnt[c[i - 1]] < MAGIC)
		{
			cout << f(i, c[i - 1]);
		}
		else
			cout << ac.getLink(i);
	}
	cout << "\n";
		
	return 0;
}

详细

Test #1:

score: 100
Accepted
time: 0ms
memory: 26040kb

input:

2
0 0
1 2

output:

0 0

result:

ok 2 number(s): "0 0"

Test #2:

score: 0
Accepted
time: 0ms
memory: 24288kb

input:

2
0 1
1 1

output:

0 1

result:

ok 2 number(s): "0 1"

Test #3:

score: 0
Accepted
time: 0ms
memory: 26304kb

input:

1
0
1

output:

0

result:

ok 1 number(s): "0"

Test #4:

score: -100
Wrong Answer
time: 3ms
memory: 24436kb

input:

50
0 1 1 1 0 0 4 4 3 7 1 11 1 11 2 15 13 11 4 11 5 7 22 17 4 19 19 26 19 27 3 17 9 4 14 8 15 33 33 33 9 40 24 18 5 28 10 1 47 25
20 20 31 1 43 3 3 21 3 3 3 22 43 3 1 20 3 43 43 20 3 20 1 3 20 20 3 1 43 3 20 20 20 29 3 3 3 3 20 1 3 3 3 3 20 3 3 25 3 1

output:

0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0

result:

wrong answer 2nd numbers differ - expected: '1', found: '0'