【BZOJ4530】大融合(Link-Cut Tree)

题面

讨厌权限题!!!

Loj链接

题目描述

小强要在 N个孤立的星球上建立起一套通信系统。这套通信系统就是连接 N个点的一个树。这个树的边是一条一条添加上去的。在某个时刻,一条边的负载就是它所在的当前能够联通的树上路过它的简单路径的数量。

例如,在上图中,现在一共有五条边。其中,(3,8)这条边的负载是 6,因为有六条简单路径 2−3−8, 2−3−8−7, 3−8, 3−8−7, 4−3−8, 4−3−8−72-3-8,\ 2-3-8-7,\ 3-8,\ 3-8-7,\ 4-3-8,\ 4-3-8-72−3−8, 2−3−8−7, 3−8, 3−8−7, 4−3−8, 4−3−8−7 路过了 (3,8)。

现在,你的任务就是随着边的添加,动态的回答小强对于某些边的负载的询问。

输入格式

第一行包含两个整数 N,QN,QN,Q,表示星球的数量和操作的数量。星球从 111 开始编号。

接下来的 QQQ 行,每行是如下两种格式之一:

A x y 表示在 xxx 和 yyy 之间连一条边。保证之前 xxx 和 yyy 是不联通的。

Q x y 表示询问 (x,y)(x,y)(x,y) 这条边上的负载。保证 xxx 和 yyy 之间有一条边。

输出格式

对每个查询操作,输出被查询的边的负载。

样例

样例输入

8 6

A 2 3

A 3 4

A 3 8

A 8 7

A 6 5

Q 3 8

样例输出

6

数据范围与提示

对于所有数据,\(1≤N,Q≤100000\)

题解

\(Link-Cut\ Tree\)维护子树信息

不仅仅维护实儿子

还需要维护虚儿子

就相当于在原树中的儿子数量啦

我也不知道为什么

。。。

以后知道了就补一下

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<set>
#include<map>
#include<vector>
#include<queue>
using namespace std;
#define MAX 120000
#define lson (t[x].ch[0])
#define rson (t[x].ch[1])
inline int read()
{
int x=0,t=1;char ch=getchar();
while((ch<'0'||ch>'9')&&ch!='-')ch=getchar();
if(ch=='-')t=-1,ch=getchar();
while(ch<='9'&&ch>='0')x=x*10+ch-48,ch=getchar();
return x*t;
}
struct Node
{
int ch[2],ff;
int rev,size,sum;
}t[MAX];
int S[MAX],top;
int n,Q;
bool isroot(int x){return t[t[x].ff].ch[0]!=x&&t[t[x].ff].ch[1]!=x;}
void pushup(int x){t[x].sum=t[lson].sum+t[rson].sum+t[x].size+1;}
void rotate(int x)
{
int y=t[x].ff,z=t[y].ff;
int k=t[y].ch[1]==x;
if(!isroot(y))t[z].ch[t[z].ch[1]==y]=x;t[x].ff=z;
t[y].ch[k]=t[x].ch[k^1];t[t[x].ch[k^1]].ff=y;
t[x].ch[k^1]=y;t[y].ff=x;
pushup(y);pushup(x);
}
void pushdown(int x)
{
if(!t[x].rev)return;
swap(lson,rson);
if(lson)t[lson].rev^=1;
if(rson)t[rson].rev^=1;
t[x].rev^=1;
}
void Splay(int x)
{
S[top=1]=x;
for(int i=x;!isroot(i);i=t[i].ff)S[++top]=t[i].ff;
while(top)pushdown(S[top--]);
while(!isroot(x))
{
int y=t[x].ff,z=t[y].ff;
if(!isroot(y))
(t[y].ch[1]==x)^(t[z].ch[1]==y)?rotate(x):rotate(y);
rotate(x);
}
}
void access(int x){for(int y=0;x;y=x,x=t[x].ff)Splay(x),t[x].size+=t[rson].sum-t[y].sum,t[x].ch[1]=y,pushup(x);}
void makeroot(int x){access(x);Splay(x);t[x].rev^=1;}
void split(int x,int y){makeroot(x);access(y);Splay(y);}
void cut(int x,int y){split(x,y);t[y].ch[0]=t[x].ff=0;pushup(y);}
void link(int x,int y){makeroot(x);makeroot(y);t[x].ff=y;t[y].size+=t[x].sum;pushup(y);}
int findroot(int x){makeroot(x);while(lson)x=lson;return x;}
int main()
{
n=read();Q=read();
char ch[2];int u,v;
while(Q--)
{
scanf("%s",ch);u=read(),v=read();
if(ch[0]=='A')link(u,v);
else split(u,v),printf("%lld\n",1ll*t[u].sum*(t[v].sum-t[u].sum));
}
return 0;
}

【BZOJ4530】大融合(Link-Cut Tree)的更多相关文章

  1. [BJOI2014]大融合(Link Cut Tree)

    [BJOI2014]大融合(Link Cut Tree) 题面 给出一棵树,动态加边,动态查询通过每条边的简单路径数量. 分析 通过每条边的简单路径数量显然等于边两侧节点x,y子树大小的乘积. 我们知 ...

  2. Link Cut Tree学习笔记

    从这里开始 动态树问题和Link Cut Tree 一些定义 access操作 换根操作 link和cut操作 时间复杂度证明 Link Cut Tree维护链上信息 Link Cut Tree维护子 ...

  3. Link Cut Tree 总结

    Link-Cut-Tree Tags:数据结构 ##更好阅读体验:https://www.zybuluo.com/xzyxzy/note/1027479 一.概述 \(LCT\),动态树的一种,又可以 ...

  4. LCT总结——概念篇+洛谷P3690[模板]Link Cut Tree(动态树)(LCT,Splay)

    为了优化体验(其实是强迫症),蒟蒻把总结拆成了两篇,方便不同学习阶段的Dalao们切换. LCT总结--应用篇戳这里 概念.性质简述 首先介绍一下链剖分的概念(感谢laofu的讲课) 链剖分,是指一类 ...

  5. [CodeForces - 614A] A - Link/Cut Tree

    A - Link/Cut Tree Programmer Rostislav got seriously interested in the Link/Cut Tree data structure, ...

  6. link cut tree 入门

    鉴于最近写bzoj还有51nod都出现写不动的现象,决定学习一波厉害的算法/数据结构. link cut tree:研究popoqqq那个神ppt. bzoj1036:维护access操作就可以了. ...

  7. Codeforces Round #339 (Div. 2) A. Link/Cut Tree 水题

    A. Link/Cut Tree 题目连接: http://www.codeforces.com/contest/614/problem/A Description Programmer Rostis ...

  8. Link/cut Tree

    Link/cut Tree 一棵link/cut tree是一种用以表示一个森林,一个有根树集合的数据结构.它提供以下操作: 向森林中加入一棵只有一个点的树. 将一个点及其子树从其所在的树上断开. 将 ...

  9. 洛谷P3690 Link Cut Tree (模板)

    Link Cut Tree 刚开始写了个指针版..调了一天然后放弃了.. 最后还是学了黄学长的板子!! #include <bits/stdc++.h> #define INF 0x3f3 ...

随机推荐

  1. bootloader总体操作设计

    bootloarder设计蓝图(不想做设计师的程序员不是好程序员):bootloarder的作用:将linux内核启动起来设计方法:模仿u-bootu-boot:支持多种嵌入式cpu的bootloar ...

  2. 使用matlab生成sine波mif文件

    使用matlab生成sine波mif文件 作者:lee神 在使用altera 的FPGA中的rom过程中常常会使用到.mif文件或.hex文件.对于初学者,无论mif还是hex都是很令人疑惑的东西,这 ...

  3. linux、windows系统间传输文件

    日常工作中经常涉及到系统间的文件传输,下面就简单说一下常用的方法   linux--windows      工具:winscp.SecureCRT.Zmodem(sz, rz)   linux--l ...

  4. 深入java虚拟机学习 -- 类的加载机制(续)

    昨晚写 深入java虚拟机学习 -- 类的加载机制 都到1点半了,由于第二天还要工作,没有将上篇文章中的demo讲解写出来,今天抽时间补上昨晚的例子讲解. 这里我先把昨天的两份代码贴过来,重新看下: ...

  5. Entity Framework——记录执行的命令信息

    有两种方法可以记录执行的SQl语句: 使用DbContext.Database.Log属性 实现IDbCommandInterceptor接口 一 使用DbContext.Database.Log属性 ...

  6. Tensorflow中实现BN为什么需要加入这个额外依赖?见CS231N作业源码

    batch normalization in tensorflow requires this extra dependency 为什么加上这两句? extra_update_ops = tf.get ...

  7. nyoj1204 魔法少女 线性DP

    d[i][0]表示到达第i层,且在第i层没有使用魔法的最少时间 d[i][1]表示到达第i层,且在第i层使用魔法通过一层 d[i][2]表示到达第i层,且在第i层使用魔法通过两层 状态转移方程: d[ ...

  8. JavaScript设计模式之策略模式

    所谓"条条道路通罗马",在现实中,为达到某种目的往往不是只有一种方法.比如挣钱养家:可以做点小生意,可以打分工,甚至还可以是偷.抢.赌等等各种手段.在程序语言设计中,也会遇到这种类 ...

  9. NLP+语义分析(四)︱中文语义分析研究现状(CIPS2016、角色标注、篇章分析)

    摘录自:CIPS2016 中文信息处理报告<第二章 语义分析研究进展. 现状及趋势>P14 CIPS2016> 中文信息处理报告下载链接:http://cips-upload.bj. ...

  10. Linux OpenSSH后门的添加与防范

    引言:相对于Windows,Linux操作系统的密码较难获取.不过很多Linux服务器配置了OpenSSH服务,在获取root权限的情况下,可以通过修改或者更新OpenSSH代码等方法,截取并保存其S ...