Description
Byteasar is a very tangled person. Every time he passed the Bytetown, he knew there were at least 2 different paths to choose from, which led him to take a long time to decide which way to go. Byteasar recently heard of Bytetown's road plan, he may be the only one who is happy with it-he has a chance to get rid of his troubles.
In the Byteasar there is a total of n fork, connecting M two-way road. The two paths are completely different when and only if they have no public roads (but are allowed to pass the same fork).
Byteasar wants to know x y if there is a completely different path for the two fork.
Input
The first line is 3 integers: n, m, z (2<=n<=100000, 1<=m,z<=100000) , respectively: N fork, M Edge, number of events Z. The fork is numbered 1~n.
The following M line: ai, bi (1<=ai,bi<= n, ai!=bi) , describes an edge
Then the following Z-line describes the event: ti, ci, di (t=‘Z‘ or ‘P‘, 1<=ci,di<=n, ci!=di) . Events are sorted by time.
- When
t=‘Z‘ , represents deleting an edge (ci, di) , ensure that the edge is not deleted before. Note that the side can be deleted all!
- When
t=‘P‘ asked if there are a pair of completely different paths from Ci to Di.
Output
For each set of queries, if present, output TAK , otherwise output NIE .
Sample Input7 8 7
1 2
1 3
1 4
2 3
3 4
3 7
7 4
5 6
Z 1 4
P 1 3
P 2 4
Z 1 3
P 1 3
Z 6 5
P 5 6
Sample OutputTAK
TAK
NIE
NIE
have done BZOJ2959 long-distance running words This problem is very simple, first time back to the edge of the cut to add edge, and then use LCT to maintain the side-dual-link components and contraction ring, see code. The first time I paddle LCT was stuck!!! The foreigner is too strong!!! It seems that after writing LCT can not be lazy.
#include <cstdio> #include <cctype> #include <cstring> #include <algorithm> #define LC ch[x][0]# Define RC Ch[x][1] #define REP (i,s,t) for (int. i=s;i<=t;i++) #define DWN (I,S,T) for (int. i=s;i>=t;i--) #define REN for ( int i=first[x];i;i=next[i]) using namespace Std;const int Buffersize=1<<16;char buffer[buffersize],*head,*tail; inline char Getchar () {if (head==tail) {int l=fread (Buffer,1,buffersize,stdin); tail= (Head=buffer) +l;} return *head++;} inline int read () {int X=0,f=1;char c=getchar (); for (;! IsDigit (c); C=getchar ()) if (c== '-') f=-1; for (; IsDigit (c); C=getchar ()) x=x*10+c-' 0 '; return x*f;} const int Maxn=100010;int n,m,z,ans[maxn],pa[maxn],pa2[maxn];struct Edge {int U,v;bool operator < (const edge& THS ) const {return u<ths.u| | (U==THS.U&&V<THS.V);}} E[maxn],q[maxn];int findset (int x) {return x==pa[x]?x:pa[x]=findset (pa[x]);} int FINDRT (int x) {return X==PA2[X]?X:PA2[X]=FINDRT (pa2[x]);} int Tp[maxn],del[maxn];int PRE[MAXN],FA[MAXN],CH[MAXN][2],flip[maxn];void pushdown (int x) {if (flip[x]) {flip[lc]^=1;flip[rc]^=1;swap (LC,RC); flip[x]=0;}} void rotate (int x) {int y=pre[x],z=pre[y],d=ch[y][0]==x;ch[y][d^1]=ch[x][d];p re[ch[x][d]]=y;ch[z][ch[z][1]==y]=x; Pre[x]=z;ch[x][d]=y;pre[y]=x;} int s[maxn],top;void splay (int x) {for (int i=x;i;i=pre[i]) s[++top]=i;if (top!=1) Fa[x]=fa[s[top]],fa[s[top]]=0;while ( Top) Pushdown (s[top--]), while (Pre[x]) {int y=pre[x],z=pre[y]; if (Pre[y]) if (ch[y][0]==x^ch[z][0]==y) rotate (x); else rotate (y); Rotate (x); }}void access (int x) {for (int y=0;x;x=findset (fa[x))) {splay (x);p re[ch[x][1]]=0;fa[ch[x][1]]=x;ch[x][1]=y;pre[y]=x; Y=x;}} void makeroot (int x) {access (x); splay (x); flip[x]^=1;} void link (int x,int y) {makeroot (x); fa[x]=y;} void Dfs (int x,int y) {if (!x) return;pushdown (x);p a[findset (x)]=findset (y);d FS (ch[x][0],y);d FS (ch[x][1],y); Ch[x][0] =ch[x][1]=0;} void cycle (int x,int y) {makeroot (x); Access (y); splay (y);d FS (y,y); void Add (int x,int y) {x=findset (x); Y=findset (y); if (x==y) returnif (FINDRT (x)!=findrt (y)) Link (x, y), pa2[findrt (×)]=findrt (y), Else cycle (x, y);} int main () {n=read (); M=read (); Z=read (); Rep (i,1,m) {e[i].u=read (), E[i].v=read (); if (E[I].U>E[I].V) swap (e[i].u,e[ I].V);} Sort (e+1,e+m+1), Rep (i,1,z) {char C=getchar (), while (!isalpha (c)) C=getchar (); tp[i]= (c== ' P '); Q[i].u=read (); Q[i].v=read (), if (Q[I].U>Q[I].V) swap (Q[I].U,Q[I].V), if (!tp[i]) {int l=1,r=m,mid;while (L<R) if (e[mid=l+r> >1]<q[i]) l=mid+1; else r=mid;del[l]=1;}} Rep (i,1,n) pa[i]=pa2[i]=i;rep (i,1,m) if (!del[i]) Add (E[I].U,E[I].V);d wn (i,z,1) {if (!tp[i]) Add (Q[I].U,Q[I].V); else Ans[i]=findset (Q[I].U) ==findset (Q[I].V);} Rep (i,1,z) if (Tp[i]) puts (ans[i]? " TAK ":" NIE "); return 0;}
BZOJ3069: [Pa2011]hard Choice difficult choice