社区讨论

为什么 BZOJ和UOJ上100分,洛谷上12分?

P3823[NOI2017] 蚯蚓排队参与者 1已保存回复 0

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
0 条
当前快照
1 份
快照标识符
@mi6wjdoh
此快照首次捕获于
2025/11/20 11:59
4 个月前
此快照最后确认于
2025/11/20 11:59
4 个月前
查看原帖
CPP
#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#define For(i, a, b) for (i = a; i <= b; i++)
#define Rof(i, a, b) for (i = a; i >= b; i--)
#define Edge(u) for (int e = adj[u]; e; e = nxt[e])
using namespace std;
inline int read() {
	int res = 0; bool bo = 0; char c;
	while (((c = getchar()) < '0' || c > '9') && c != '-');
	if (c == '-') bo = 1; else res = c - 48;
	while ((c = getchar()) >= '0' && c <= '9')
		res = (res << 3) + (res << 1) + (c - 48);
	return bo ? ~res + 1 : res;
}
typedef unsigned long long ull;
const int N = 2e5 + 5, PYZ = 19260817, M = 1e7 + 7, E = 55, 
Z = 126e5 + 5, ZZQ = 998244353;
int n, m, ecnt, a[N], pre[Z], nxt[Z], adj[PYZ], cnt[Z], le[N], ri[N];
ull has[M], hasl[E], hasr[E], go[Z], pw[E];
char s[M];
int query(ull has) {
	int u = has % PYZ;
	Edge(u) if (go[e] == has) return e;
	return -1;
}
void ins(ull has) {
	int e;
	if ((e = query(has)) != -1) return (void) (cnt[e]++);
	int u = has % PYZ; ecnt++;
	if (adj[u]) pre[adj[u]] = ecnt; nxt[ecnt] = adj[u];
	adj[u] = ecnt; go[ecnt] = has; cnt[ecnt] = 1;
}
void del(ull has) {
	int e = query(has);
	if (cnt[e] > 1) return (void) (cnt[e]--);
	if (!pre[e]) adj[has % PYZ] = nxt[e];
	else nxt[pre[e]] = nxt[e];
	if (nxt[e]) pre[nxt[e]] = pre[e];
}
int queryt(ull has) {
	int e = query(has);
	return e == -1 ? 0 : cnt[e];
}
void mer(int x, int y) {
	ri[x] = y; le[y] = x;
	int i, j, tt = 1, ff = 1;
	hasl[tt] = a[x]; hasr[ff] = a[y];
	while (le[x] && tt < 49) x = le[x],
		hasl[++tt] = hasl[tt - 1] + pw[tt - 1] * a[x];
	while (ri[y] && ff < 49) y = ri[y],
		hasr[++ff] = hasr[ff - 1] * 7 + a[y];
	For (i, 1, tt) For (j, 1, min(50 - i, ff))
		ins(hasl[i] * pw[j] + hasr[j]);
}
void spl(int x) {
	int y = ri[x];
	ri[x] = le[y] = 0;
	int i, j, tt = 1, ff = 1;
	hasl[tt] = a[x]; hasr[ff] = a[y];
	while (le[x] && tt < 49) x = le[x],
		hasl[++tt] = hasl[tt - 1] + pw[tt - 1] * a[x];
	while (ri[y] && ff < 49) y = ri[y],
		hasr[++ff] = hasr[ff - 1] * 7 + a[y];
	For (i, 1, tt) For (j, 1, min(50 - i, ff))
		del(hasl[i] * pw[j] + hasr[j]);
}
int query(int len, int k) {
	int i, res = 1;
	For (i, 1, len) has[i] = has[i - 1] * 7 + s[i] - '0';
	For (i, 1, len - k + 1)
		res = 1ll * res * queryt(has[i + k - 1] - has[i - 1] * pw[k])
			% ZZQ;
	return res;
}
int main() {
	int i, op, x, y;
	n = read(); m = read();
	pw[0] = 1;
	For (i, 1, n) a[i] = read();
	For (i, 1, 50) pw[i] = pw[i - 1] * 7;
	For (i, 1, n) ins(a[i]);
	while (m--) {
		op = read();
		if (op == 1) x = read(), y = read(), mer(x, y);
		else if (op == 2) x = read(), spl(x);
		else scanf("%s", s + 1), x = read(),
			printf("%d\n", query(strlen(s + 1), x));
	}
	return 0;
}

回复

0 条回复,欢迎继续交流。

正在加载回复...