2819:nim time limit:20 Sec Memory limit:128 MB
submit:2045 solved:795
[Submit] [Status] [Discuss] Description
Vfleaking, a famous game designer, has recently been hooked on Nim. Ordinary Nim game for: Two people to play, n heap of stones, each turn can take one of the piles of any number, can be taken, but can not be taken. Who can not take who loses. There is a winning strategy for this game. So Vfleaking decided to write a platform to play Nim games to pit the players.
In order to design a beautiful initial situation, vfleaking in the following ways to find inspiration: Take a lot of stones, put them into a pile of piles, to each heap number 1,2,3,4,... N, in the heap and the heap between the edge, there is no self-ring and heavy edge, from any heap to any heap only one path can be reached. Then he kept doing the following:
1. Randomly select two heap v,u, ask if you play NIM game in the gravel heap on the path between V and U, if there is a winning strategy, if there is, vfleaking will consider these gravel heap as one of the initial situations to pit the players.
2. Change the number of stones in Heap V to K.
Because vfleaking was too lazy, he did not bother to do it himself. Please write a program to help him.
Input
The first row is a number n, which indicates how many stones are in the heap.
The next line, number I, indicates how many stones are in the heap.
Next n-1 line, two numbers per line of V,u, representing the v,u between a side directly connected.
The next number Q, which represents the number of operations.
Next Q line, each line begins with one character:
If it is Q, then there are two number v,u, asking if there is a winning strategy if you play Nim in the gravel heap on the path between V and U.
If it is C, then there are two number v,k, which means that the number of stones in the heap V is changed to K.
For 100% of data:
1≤n≤500000, 1≤q≤500000, 0≤ the number of stones per heap at any time ≤32767
There are 30% of the data:
The gravel heap makes up a chain, and these 3 points will cause you to have a Dfs burst stack (maybe you don't have DFS?). )。 Other data Dfs visually does not explode.
Note: The range of stone numbers is 0 to Int_max
Output
For each q, the output line is yes or no, which represents the answer to the query.
Sample Input"Sample Input"
5
1 3 5) 2 5
1 5
3 5
2 5
1 4
6
Q 1 2
Q 3 5
C 3 7
Q 1 2
Q 2 4
Q 5 3
Sample Output
Yes
No
Yes
Yes
Yes
Test instructions: Chinese does not explain
Puzzle: For a point pair (u,v) Their path XOR value is Xorsum[u]^xorsum[v]^val[lca (u,v)].xorsum[i] represents the XOR from the root node to the current node I, how to maintain this value on the tree? It's not good to maintain, so consider turning it into a sequence. , so you can use the DFS sequence to convert the tree into a sequence, and then use the interval update, single-point evaluation can be, update the value of the update is change = Val[x]^y, my LCA template has a problem, WA n fat. I got a better one. LCA template = =, and one point is that the winning state of the NIM game is XOR and not 0
#pragmaComment (linker, "/stack:1024000000,1024000000")#include<bits/stdc++.h>using namespacestd;Const intN =500005;Const intdeg= -;structedge{intTo,next;} Edge[n<<1];intN,cnt,tot,num,head[n];int inch[N], out[N];intVal[n],c[n];voidAddedge (intUintv) {edge[tot].to=v; Edge[tot].next=Head[u]; Head[u]= tot++;}/************* LCA calls DFS (1,0,0) and Getanc () ***************/intAnc[n][deg],dep[n];voidDfsintUintFaintd) {Dep[u]=D; anc[u][0]=FA; for(inti=head[u];i!=-1; i=edge[i].next)if(EDGE[I].TO!=FA) DFS (edge[i].to,u,d+1);}voidGetanc () { for(intI=1; i<deg;i++) for(intj=1; j<=n;j++) Anc[j][i]=anc[anc[j][i-1]][i-1];}intSwimintUintH) { intI=0; while(H) {if(h&1) u=Anc[u][i]; I++; H>>=1; } returnu;}intLcaintUintv) { if(dep[u]<Dep[v]) swap (U,V); U=swim (u,dep[u]-Dep[v]); if(U==V)returnu; for(inti=deg-1; i>=0; i--) { if(anc[u][i]!=Anc[v][i]) {u=Anc[u][i]; V=Anc[v][i]; } } returnanc[u][0];}/*****************************/voidDFS1 (intUintFA) {num++; inch[U] =num; for(intK=head[u]; k!=-1; k=Edge[k].next) { intv =edge[k].to; if(V==FA)Continue; DFS1 (V,u); } out[U] =num;}voidinit () {memset (head,-1,sizeof(head)); Memset (c,0,sizeof(c)); Tot=0, cnt =0, num =0 ;}intLowbit (intx) { returnx& (-x);}voidUpdateintXintv) { for(intI=x; i<=n; i+=lowbit (i)) {C[i]^=v; }}intGetsum (intx) { intAns =0; for(intI=x; i>=1; i-=lowbit (i)) {ans^=C[i]; } returnans;}intMain () {scanf ("%d",&N); Init (); for(intI=1; i<=n; i++) scanf ("%d",&Val[i]); for(intI=1; i<n; i++) { intu,v; scanf ("%d%d",&u,&v); Addedge (U,V); Addedge (V,u); } DFS1 (1,-1); DFS (1,0,0); Getanc (); for(intI=1; i<=n; i++) {Update (inch[I],val[i]); Update ( out[i]+1, Val[i]); } intQ; scanf ("%d",&q); while(q--) { Chars[5]; intx, y; scanf ("%s%d%d",s,&x,&y); if(s[0]=='Q') { int_lca =LCA (x, y); intAns = getsum (inch[x]) ^getsum (inch[y]) ^Val[_lca]; if(ANS) printf ("yes\n"); Elseprintf"no\n"); } Else { intChange = val[x]^X; Update (inch[X],change]; Update ( out[x]+1, change); VAL[X]=y; } } return 0;}
Bzoj 2819 (Dfs sequence + tree-like array + game +LCA)