题意:给定一棵树,要求维护以下操作:

1.删除连接(x,y)的边

2.将(x,y)之间连边

3.询问某点子树大小

对于100%的数据n<=200000,m<=100000

思路:第一道有加边删边的LCT

讲一下自己对LCT各个操作的理解

Access:最基本的操作,将一个点到LCT的根的点全部修改为重(实)边

可以理解为“全选操作”,配合Splay操作可以取出某段区间的信息

Splay:将X旋转到它所在链的顶部,这样就相当于将这条链中的信息集中到了X这个点上

LCT的splay要用栈pushdown维护的原因是普通splay中splay操作前这些信息已经在Findkth的时候下传

而LCT没有,需要手动下传

Findroot:找到LCT的根,先Access+splay,因为LCT是按照深度维护的,所以一直往左走,找到深度最小的就是根

Makeroot:将X设置为LCT的根,Access+splay,因为上下翻转了所以要打翻转标记

Link:链接两个不在同一条链上的点,Makeroot(x),fa[x]=y

split:取出(x,y)这段区间的信息,Makeroot(x),Access(y),splay(y),信息在y点上

此题输出左儿子的子树大小即可

 var t:array[..,..]of longint;
next,fa,rev,size,q:array[..]of longint;
n,m,i,x,y,tmp,top:longint; function isroot(x:longint):boolean;
begin
if (t[fa[x],]<>x)and(t[fa[x],]<>x) then exit(true);
exit(false);
end; procedure swap(var x,y:longint);
var t:longint;
begin
t:=x; x:=y; y:=t;
end; procedure pushup(x:longint);
var l,r:longint;
begin
l:=t[x,]; r:=t[x,];
size[x]:=size[l]+size[r]+;
end; procedure pushdown(x:longint);
var l,r:longint;
begin
l:=t[x,]; r:=t[x,];
if rev[x]> then
begin
rev[x]:=rev[x] xor ; rev[l]:=rev[l] xor ; rev[r]:=rev[r] xor ;
swap(t[x,],t[x,]);
end;
end; procedure rotate(x:longint);
var y,z,l,r:longint;
begin
y:=fa[x]; z:=fa[y];
if t[y,]=x then l:=
else l:=;
r:=l xor ;
while not isroot(y) do
begin
if t[z,]=y then t[z,]:=x
else t[z,]:=x;
end;
fa[x]:=z; fa[y]:=x; fa[t[x,r]]:=y;
t[y,l]:=t[x,r]; t[x,r]:=y;
pushup(y);
pushup(x);
end; procedure splay(x:longint);
var y,z,k:longint;
begin
inc(top); q[top]:=x;
k:=x;
while not isroot(k) do
begin
inc(top); q[top]:=fa[k];
k:=fa[k];
end;
while top> do
begin
pushdown(q[top]);
dec(top);
end; while not isroot(x) do
begin
y:=fa[x]; z:=fa[y];
if not isroot(y) then
begin
if (t[y,]=x)xor(t[z,]=y) then rotate(x)
else rotate(y);
end;
rotate(x);
end;
end; procedure access(x:longint);
var last:longint;
begin
last:=;
while x> do
begin
splay(x); t[x,]:=last; //pushup(x);
last:=x; x:=fa[x];
end;
end; procedure makeroot(x:longint);
begin
access(x); splay(x); rev[x]:=rev[x] xor ;
end; procedure link(x,y:longint);
begin
makeroot(x); fa[x]:=y;
end; procedure split(x,y:longint);
begin
makeroot(x); access(y); splay(y);
end; procedure cut(x,y:longint);
begin
makeroot(x); access(y); splay(y); t[y,]:=; fa[x]:=;
end; function min(x,y:longint):longint;
begin
if x<y then exit(x);
exit(y);
end; begin
assign(input,'bzoj2002.in'); reset(input);
assign(output,'bzoj2002.out'); rewrite(output);
readln(n);
for i:= to n do
begin
read(x);
fa[i]:=x+i; size[i]:=;
if fa[i]>n then fa[i]:=n+;
next[i]:=fa[i];
end;
size[n+]:=;
readln(m);
for i:= to m do
begin
read(x);
case x of
:
begin
read(y); inc(y);
split(n+,y);
writeln(size[t[y,]]);
end;
:
begin
read(x,y);
inc(x); tmp:=min(x+y,n+);
cut(x,next[x]); link(x,tmp); next[x]:=tmp;
end;
end;
end;
close(input);
close(output);
end.

【BZOJ2002】弹飞绵羊(LCT)的更多相关文章

  1. bzoj2002 弹飞绵羊 lct版

    这道题就是维护一个有根的lct 一开始建树全部建虚边 求多少次弹出就是求他到根的距离(根为n+1) 这里有个小技巧 将n+1作为根而没有虚根操作起来会比较方便 #include<cstdio&g ...

  2. BZOJ-2002 弹飞绵羊 Link-Cut-Tree (分块)

    2002: [Hnoi2010]Bounce 弹飞绵羊 Time Limit: 10 Sec Memory Limit: 259 MB Submit: 6801 Solved: 3573 [Submi ...

  3. 洛谷P3203 [HNOI2010] 弹飞绵羊 [LCT]

    题目传送门 弹飞绵羊 题目描述 某天,Lostmonkey发明了一种超级弹力装置,为了在他的绵羊朋友面前显摆,他邀请小绵羊一起玩个游戏.游戏一开始,Lostmonkey在地上沿着一条直线摆上n个装置, ...

  4. P3203 [HNOI2010]弹飞绵羊(LCT)

    弹飞绵羊 题目传送门 解题思路 LCT. 将每个节点的权值设为\(1\),连接\(i\)和\(i+ki\),被弹飞就连上\(n\),维护权值和\(sum[]\).从\(j\)弹飞需要的次数就是\(sp ...

  5. [Luogu P3203] [HNOI2010]弹飞绵羊 (LCT维护链的长度)

    题面 传送门:洛谷 Solution 这题其实是有类似模型的. 我们先考虑不修改怎么写.考虑这样做:每个点向它跳到的点连一条边,最后肯定会连成一颗以n+1为根的树(我们拿n+1代表被弹出去了).题目所 ...

  6. BZOJ 2002: [Hnoi2010]Bounce 弹飞绵羊 LCT

    2002: [Hnoi2010]Bounce 弹飞绵羊 Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOn ...

  7. [BZOJ2002] [Hnoi2010] Bounce 弹飞绵羊 (LCT)

    Description 某天,Lostmonkey发明了一种超级弹力装置,为了在他的绵羊朋友面前显摆,他邀请小绵羊一起玩个游戏.游戏一开始,Lostmonkey在地上沿着一条直线摆上n个装置,每个装置 ...

  8. BZOJ2002[Hnoi2010]弹飞绵羊——LCT

    题目描述 某天,Lostmonkey发明了一种超级弹力装置,为了在他的绵羊朋友面前显摆,他邀请小绵羊一起玩个游戏.游戏一开始,Lostmonkey在地上沿着一条直线摆上n个装置,每个装置设定初始弹力系 ...

  9. [bzoj] 2002 弹飞绵羊 || LCT

    原题 简单的LCT练习题. 我们发现对于一个位置x,他只能跳到位置x+k,也就是唯一的父亲去.加入我们将弹飞的绵羊定义为跳到了n+1,那么这就形成了一棵树.而因为要修改k,所以这颗树是动态连边的,那么 ...

  10. 【HNOI2010】弹飞绵羊 - LCT

    题目描述 某天,Lostmonkey发明了一种超级弹力装置,为了在他的绵羊朋友面前显摆,他邀请小绵羊一起玩个游戏.游戏一开始,Lostmonkey在地上沿着一条直线摆上n个装置,每个装置设定初始弹力系 ...

随机推荐

  1. fckeditor配置详解

    使用配置设置: . FCKConfig.CustomConfigurationsPath = '' ; // 自定义配置文件路径和名称 . FCKConfigFCKConfig.EditorAreaC ...

  2. word2vec 中的数学原理详解(二)预备知识

    版权声明:本文为博主原创文章,未经博主允许不得转载. https://blog.csdn.net/peghoty/article/details/37969635 https://blog.csdn. ...

  3. 计算机应用第七次作业 html制作个人音乐播放站点

    计算机应用第七次作业 html制作个人音乐播放站点 请访问下边网址查看具体操作: http://www.cnblogs.com/qingyundian/p/7878892.html

  4. c++:printf和cout那个更好更快些

    现在群里在讨论cout和printf那个快的问题,但我个人觉得printf好: 因为:printf对于一些数据大,以及保留小数位,字符……可以显示出明显的优势如“%s %d %c…………” 虽然pri ...

  5. luogu P1966 火柴排队 (逆序对)

    luogu P1966 火柴排队 题目链接:https://www.luogu.org/problemnew/show/P1966 显然贪心的想,排名一样的数相减是最优的. 证明也很简单. 此处就不证 ...

  6. 对Java提供的锁机制的一些思考

    Java的数据会在CPU.Register.Cache.Heap和Thread stack之间进行复制操作,而前面四个都是在Java Threads之间共享,因此Java的锁机制主要用于解决Racin ...

  7. docker系列之镜像服务器

    docker 的镜像服务器 docker-registry 是 docker 项目的组成部分. 前面在谈 docker 的命令时, 它的 pull/push 命令就是和镜像服务器打交道. 并且, do ...

  8. RabbitMQ 初体验

    概述 RabbitMQ是一款消息队列中间件.他提供了几乎覆盖所有语言的SDK与文档,简直强大的不的了.要详细的去了解学习RabbitMQ,我建议还是看官方文档吧.http://www.rabbitmq ...

  9. perl学习之子程序

    一.定义子程序即执行一个特殊任务的一段分离的代码,它可以使减少重复代码且使程序易读.PERL中,子程序可以出现在程序的任何地方.定义方法为:sub subroutine{statements;}二.调 ...

  10. 《嵌入式linux应用程序开发标准教程》笔记——9.多线程编程

    线程是轻量级进程,创建线程的开销要比进程小得多,在大型程序中应用广泛. 9.1 线程概述 进程包含自己的代码.数据.堆栈.资源等等,创建和切换的开销比较大: 线程是轻量级的进程,调度的最小单元,同一个 ...