社区讨论

萌新求助LCT

P3203[HNOI2010] 弹飞绵羊参与者 8已保存回复 13

讨论操作

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

当前回复
13 条
当前快照
1 份
快照标识符
@mi7cmp3d
此快照首次捕获于
2025/11/20 19:29
4 个月前
此快照最后确认于
2025/11/20 21:58
4 个月前
查看原帖
这个这个超神奇地MLE了我天
试过splay前的下放标记手动栈就RE了QAQ
求dalao帮忙看下代码我去弄盒饭就回来OvO
CPP
#include <cstdio>
using namespace std;
const int MAXN = 200010;
struct splay {
	int fa,son[2],siz,rot;
} e[MAXN];
int v[MAXN];
int min(int x,int y) {return x < y ? x : y;}
inline int r()
{
	char q = getchar(); int x = 0;
	while (q < '0' || q > '9') q = getchar();
	while ('0' <= q && q <= '9')
		x = (x << 3) + (x << 1) + q - (3 << 4),q = getchar();
	return x;
}
inline short pdroot(int x)
{
	return e[e[x].fa].son[0] != x && e[e[x].fa].son[1] != x;
}
inline void pushdown(int x)
{
	if (!e[x].rot) return;
	int bot = e[x].son[0];
	e[x].son[0] = e[x].son[1];
	e[x].son[1] = bot;
	e[e[x].son[0]].rot ^= 1;
	e[e[x].son[1]].rot ^= 1;
	e[x].rot = 0;
}
inline void change(int x)
{
	if (!pdroot(x)) change(e[x].fa);
	pushdown(x);
}
inline void update(int x)
{
	e[x].siz = e[e[x].son[0]].siz + e[e[x].son[1]].siz + 1;
}
inline void rotate(int x)
{
	int y = e[x].fa,z = e[y].fa,mode = e[y].son[0] == x;
	if (!pdroot(y)) e[z].son[e[z].son[1] == y] = x;
	e[x].fa = z;
	e[y].son[mode ^ 1] = e[x].son[mode];
	e[e[x].son[mode]].fa = y;
	e[x].son[mode] = y;
	e[y].fa = x;
	update(y);
	update(x);
}
inline void splay(int x)
{
	change(x);
	while (!pdroot(x))
	{
		int y = e[x].fa,z = e[y].fa;
		if (!pdroot(y)) {
			if ((e[z].son[0] == y) ^ (e[y].son[0] == x)) rotate(x);
			else rotate(y);
		} rotate(x);
	}
}
inline void access(int x)
{
	for (int y = 0 ; x ; y = x,x = e[x].fa)
	{
		splay(x);
		e[x].son[1] = y;
		update(x);
	}
}
inline void makeroot(int x)
{
	access(x);
	splay(x);
	e[x].rot ^= 1;
}
inline void link(int x,int y)
{
	makeroot(x);
	e[x].fa = y;
}
inline void del(int x,int y)
{
	makeroot(x);
	access(y);
	splay(y);
	e[y].son[0] = 0,e[x].fa = 0;
}
inline int get(int x,int y)
{
	makeroot(x);
	access(y);
	splay(y);
	return e[y].siz;
}
int main()
{
	int n = r();
	for (int a = 1 ; a <= n + 1 ; ++ a) e[a].siz = 1;
	for (int a = 1 ; a <= n ; ++ a)
	{
		v[a] = a + r();
		link(min(v[a],n + 1),a);
	}
	int m = r();
	while (m--)
	{
		int mode = r(),x = r() + 1;
		if (mode == 1) {printf("%d\n",get(x,n + 1) - 1); continue;}
		int y = r();
		del(x,v[x]);
		v[x] = x + y;
		link(min(v[x],n + 1),x);
	}
	return 0;
}

回复

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

正在加载回复...