传送门:【BZOJ】2049 [Sdoi2008]Cave 洞穴勘测
题目分析:模板题
代码如下:
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std ;
const int MAXN = 10005 ;
struct Node* null ;
struct Node {
Node* c[2] ;
Node* f ;
int flip ;
void newnode () {
c[0] = c[1] = f = null ;
flip = 0 ;
}
void reverse () {
if ( this == null ) return ;
swap ( c[0] , c[1] ) ;
flip ^= 1 ;
}
void link_child ( Node* o , int d ) {
c[d] = o ;
o->f = this ;
}
int is_root () {
return f == null || f->c[0] != this && f->c[1] != this ;
}
void push_down () {
if ( flip ) {
c[0]->reverse () ;
c[1]->reverse () ;
flip = 0 ;
}
}
void sign_down () {
if ( !is_root () ) f->sign_down () ;
push_down () ;
}
void rotate ( int d ) {
Node* p = f ;
Node* g = p->f ;
p->link_child ( c[d] , !d ) ;
if ( !p->is_root () ) {
if ( p == g->c[0] ) g->link_child ( this , 0 ) ;
else g->link_child ( this , 1 ) ;
} else f = g ;
this->link_child ( p , d ) ;
}
void splay () {
sign_down () ;
while ( !is_root () ) {
if ( f->is_root () ) rotate ( this == f->c[0] ) ;
else {
if ( f == f->f->c[0] ) {
if ( this == f->c[0] ) f->rotate ( 1 ) , rotate ( 1 ) ;
else rotate ( 0 ) , rotate ( 1 ) ;
} else {
if ( this == f->c[1] ) f->rotate ( 0 ) , rotate ( 0 ) ;
else rotate ( 1 ) , rotate ( 0 ) ;
}
}
}
}
void access () {
Node* o = this ;
Node* x = null ;
while ( o != null ) {
o->splay () ;
o->link_child ( x , 1 ) ;
x = o ;
o = o->f ;
}
splay () ;
}
Node* find_root () {
access () ;
Node* o = this ;
while ( o->c[0] != null ) o = o->c[0] ;
return o ;
}
void make_root () {
access () ;
reverse () ;
}
void cut () {
access () ;
c[0]->f = null ;
c[0] = null ;
}
void cut ( Node* o ) {
if ( o->find_root () != find_root () ) return ;
make_root () ;
o->cut () ;
}
void link ( Node* o ) {
if ( o == this || o->find_root () == find_root () ) return ;
make_root () ;
f = o ;
}
void query ( Node* o ) {
if ( o->find_root () == find_root () ) printf ( "Yes\n" ) ;
else printf ( "No\n" ) ;
}
} ;
Node pool[MAXN] ;
Node* node[MAXN] ;
Node* cur ;
int n , m ;
void clear () {
cur = pool ;
null = cur ++ ;
null->newnode () ;
}
void solve () {
char s[20] ;
int x , y ;
clear () ;
for ( int i = 1 ; i <= n ; ++ i ) {
node[i] = cur ++ ;
node[i]->newnode () ;
}
while ( m -- ) {
scanf ( "%s%d%d" , s , &x , &y ) ;
if ( s[0] == 'C' ) node[x]->link ( node[y] ) ;
if ( s[0] == 'D' ) node[x]->cut ( node[y] ) ;
if ( s[0] == 'Q' ) node[x]->query ( node[y] ) ;
}
}
int main () {
while ( ~scanf ( "%d%d" , &n , &m ) ) solve () ;
return 0 ;
}