码迷,mamicode.com
首页 > 其他好文 > 详细

XJOI网上同步训练DAY2 T2

时间:2016-06-25 17:51:28      阅读:291      评论:0      收藏:0      [点我收藏+]

标签:

【问题描述】

火车司机出秦川跳蚤国王下江南共价大爷游长沙。每个周末勤劳的共价大爷都会开车游历长沙市。

长沙市的交通线路可以抽象成为一个技术分享 个点技术分享 条边的无向图点编号为技术分享技术分享 任意两点间均存在恰好一条路径显然两个点之间最多也只会有一条边相连。有一个包含一些点对技术分享可重集合技术分享 共价大爷的旅行路线是这样确定的每次他会选择技术分享 中的某一对点技术分享 并从技术分享 出发沿着唯一路径到达技术分享

小L是共价大爷的脑残粉为了见到共价大爷的尊容小L决定守在这张图的某条边上等待共价大爷的到来。为了保证一定能见到他显然小L必须选择共价大爷一定会经过的边——也就是所有共价大爷可能选择的路径都经过的边

现在小L想知道如果他守在某一条边是否一定能见到共价大爷。

然而长沙市总是不断的施工也就是说可能某个时刻某条边会断开同时这个时刻一定也有某条新边会出现且任意时刻图都满足任意两点间均存在恰好一条路径的条件。注意断开的边有可能和加入的新边连接着相同的两个端点。共价大爷的兴趣也会不断变化所以技术分享也会不断加入新点对或者删除原有的点对。当然L也有可能在任何时候向你提出守在某一条边是否一定能见到共价大爷的问题。你能回答小L的所有问题吗

【输入格式】

从文件travel.in 中读入数据。

输入的第一行包含一个整数技术分享 表示测试数据编号如第一组数据的技术分享 样例数据的技术分享 可以忽略。

输入的第二行包含两个整数技术分享 分别表示图中的点数以及接下来会发生的事件数事件的定义下文中会有描述。初始时技术分享 为空。

接下来技术分享 行每行两个正整数技术分享 表示点技术分享技术分享 之间有一条无向边。

接下来技术分享 行每行描述一个事件每行的第一个数技术分享 表示事件的类型。

技术分享 那么接下来有四个正整数技术分享 表示先删除连接点技术分享技术分享 的无向边保证存在这样的无向边然后加入一条连接点技术分享技术分享 的无向边保证操作后的图仍然满足题中所述条件。

技术分享 那么接下来有两个正整数技术分享 表示在技术分享 中加入点对技术分享

技术分享 那么接下来有一个正整数技术分享 表示删除第技术分享 个加入技术分享 中的点对即在第技术分享技术分享 的事件中加入技术分享 中的点对保证这个点对存在且仍然在技术分享 中。

技术分享 那么接下来有两个正整数技术分享 表示小L询问守在连接点技术分享技术分享 的边上是否一定能见到共价大爷保证存在这样的无向边且此时技术分享 不为空。

【输出格式】

输出到travel.out中。

对于每个小L的询问输出“YES”或者“NO”均不含引号表示小L一定能或者不一定能见到共价大爷。

【样例输入1】

0

5 7

1 2

1 3

2 4

1 5

2 1 5

1 1 5 2 5

4 2 5

2 1 4

4 2 5

3 1

4 2 4

【样例输出1】

YES

NO

YES

【样例说明1】

最开始将点对技术分享 加入到技术分享 中此时点1和点5之间的路径是技术分享

接着将连接点1和点5的边断开加入连接点2和点5的边我们发现图仍然满足题中所述条件且点1和点5之间的路径是技术分享 经过点了2和点5之间的边因此第一个询问答案是YES。

接着将点对技术分享 加入到技术分享 中点1和点4之间的路径是技术分享 没有经过点2和点5之间的边因此第二个询问答案是NO。

接着我们删除了第一个加入到技术分享 中的点对也就是点对技术分享 此时技术分享 中唯一的点对就是技术分享 经过了点2和点4之间的边因此最后一个询问答案是YES。

【样例输入输出2】

见下发的travel / travel1.intravel / travel1.ans

【样例输入输出3】

见下发的travel / travel2.intravel / travel2.ans这组数据中技术分享

【数据规模和约定】

数据点

技术分享 的规模

技术分享 的规模

技术分享 =

备注

1

技术分享

技术分享

1,2,3,4

 

2

技术分享

技术分享

2,4

 

3

技术分享

技术分享

2,4

 

4

技术分享

技术分享

2,3,4

 

5

技术分享

技术分享

2,3,4

 

6

技术分享

技术分享

1,2,3,4

任意时刻|技术分享

7

技术分享

技术分享

1,2,3,4

任意时刻|技术分享

8

技术分享

技术分享

1,2,3,4

 

9

技术分享

技术分享

1,2,3,4

 

10

技术分享

技术分享

1,2,3,4

 

对于所有数据技术分享技术分享技术分享

思路:本来想把边转换成点来做的,但是YY了一下发现,当把边拆掉的时候就不能维护信息了,题解的做法很玄妙:把每个路径的两个端点都异或上同一个随机值,然后询问的时候询问x子树和y子树内异或和是不是都等于ans,ans为每条边的随机值异或和。

 

  1 #include<algorithm>
  2 #include<cstdio>
  3 #include<cmath>
  4 #include<cstring>
  5 #include<iostream>
  6 int ch[500005][2],rev[500005],sum[500005],o[500005];
  7 int fa[500005];
  8 int c[500005][3],st[500005],ans;
  9 int n,m,tot;
 10 int read(){
 11     int t=0,f=1;char ch=getchar();
 12     while (ch<0||ch>9){if (ch==-) f=-1;ch=getchar();}
 13     while (0<=ch&&ch<=9){t=t*10+ch-0;ch=getchar();}
 14     return t*f;
 15 }
 16 bool isroot(int x){
 17     return ch[fa[x]][0]!=x&&ch[fa[x]][1]!=x;
 18 }
 19 void pushdown(int x){
 20     int l=ch[x][0],r=ch[x][1];
 21     if (rev[x]){
 22         rev[x]^=1;
 23         rev[l]^=1;rev[r]^=1;
 24         std::swap(ch[x][0],ch[x][1]);
 25     }
 26 }
 27 void updata(int x){
 28     int l=ch[x][0],r=ch[x][1];
 29     sum[x]=o[x]^sum[l]^sum[r];
 30 }
 31 void rotate(int x){
 32     int y=fa[x],f=ch[y][0]!=x;
 33     if (ch[y][f]=ch[x][f^1]) fa[ch[y][f]]=y;
 34     fa[x]=fa[y];if (!isroot(y)) ch[fa[y]][ch[fa[y]][0]!=y]=x;
 35     updata(ch[fa[y]=x][f^1]=y);
 36 }
 37 void splay(int x){
 38     int top=0;st[++top]=x;
 39     for (int i=x;!isroot(i);i=fa[i])
 40      st[++top]=fa[i];
 41     for (int i=top;i;i--) pushdown(st[i]);
 42     while (!isroot(x)){
 43         int y=fa[x],z=fa[y];
 44         if (!isroot(y)){
 45             if (ch[y][0]==x^ch[z][0]==y) rotate(x);
 46             else rotate(y);
 47         }
 48         rotate(x);
 49     } 
 50     updata(x);
 51 }
 52 void access(int x){
 53     for (int t=0;x;t=x,x=fa[x]){
 54         splay(x);
 55         o[x]^=sum[t]^sum[ch[x][1]];
 56         ch[x][1]=t;
 57         updata(x);
 58     }
 59 }
 60 void makeroot(int x){
 61     access(x);splay(x);rev[x]^=1;
 62 }
 63 void link(int x,int y){
 64     makeroot(x);makeroot(y);fa[x]=y;o[y]^=sum[x];updata(y);
 65 }
 66 void cut(int x,int y){
 67     makeroot(y);access(y);
 68     splay(x);
 69     fa[x]=0;o[y]^=sum[x];updata(y);
 70 }
 71 void add(int x,int y){
 72     access(x);
 73     splay(x);
 74     o[x]^=y;
 75     updata(x);
 76 }
 77 int main(){
 78     int Id=read();
 79     n=read();m=read();
 80     srand(std::abs(n-m)*3+138);
 81     for (int i=1;i<n;i++){
 82         int x=read(),y=read();
 83         link(x,y);
 84     }
 85     while (m--){
 86         int type=read();
 87         if (type==1){
 88             int x=read(),y=read(),u=read(),v=read();
 89             cut(x,y);link(u,v);
 90         }else if (type==2){
 91             tot++;
 92             c[tot][0]=read();c[tot][1]=read();int z=rand();
 93             while (!z) z=rand();
 94             c[tot][2]=z;
 95             add(c[tot][0],z);add(c[tot][1],z);ans^=z;
 96         }else if (type==3){
 97             int k=read();
 98             add(c[k][0],c[k][2]);
 99             add(c[k][1],c[k][2]);
100             ans^=c[k][2];
101         }else{
102             int x=read(),y=read();
103             makeroot(x);access(y);
104             if (o[x]==ans&&o[y]==ans) puts("YES");
105             else puts("NO");
106         }
107     }
108 }

 

XJOI网上同步训练DAY2 T2

标签:

原文地址:http://www.cnblogs.com/qzqzgfy/p/5616525.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!