BZOJ 2002 动态树

 

动态树讲解:http://www.cnblogs.com/proverbs/archive/2013/01/04/2845053.html

 

贴代码混数~

 

View Code
  1 #include <iostream>
  2 #include <algorithm>
  3 #include <cstdlib>
  4 #include <cstring>
  5 #include <cstdio>
  6 
  7 #define N 420000
  8 
  9 using namespace std;
 10 
 11 int son[N][2],sum[N],fa[N],k[N];
 12 int n,m;
 13 
 14 inline void read()
 15 {
 16     scanf("%d",&n);
 17     for(int i=1;i<=n;i++)
 18     {
 19         scanf("%d",&k[i]);
 20         fa[i]=min(i+k[i],n+1);
 21     }
 22 }
 23 
 24 inline bool isroot(int x)
 25 {
 26     return son[fa[x]][0]!=x&&son[fa[x]][1]!=x;
 27 }
 28 
 29 inline void pushup(int x)
 30 {
 31     if(x) sum[x]=sum[son[x][0]]+sum[son[x][1]]+1;
 32 }
 33 
 34 inline void zig(int x)
 35 {
 36     int y=fa[x];
 37     if(son[x][1]) son[y][0]=son[x][1],fa[son[x][1]]=y;
 38     else son[y][0]=0;
 39     fa[x]=fa[y];
 40     if(son[fa[y]][0]==y) son[fa[y]][0]=x;
 41     else if(son[fa[y]][1]==y) son[fa[y]][1]=x;
 42     fa[y]=x; son[x][1]=y;
 43     pushup(y); pushup(x);
 44 }
 45 
 46 inline void zag(int x)
 47 {
 48     int y=fa[x];
 49     if(son[x][0]) son[y][1]=son[x][0],fa[son[x][0]]=y;
 50     else son[y][1]=0;
 51     fa[x]=fa[y];
 52     if(son[fa[y]][0]==y) son[fa[y]][0]=x;
 53     else if(son[fa[y]][1]==y) son[fa[y]][1]=x;
 54     fa[y]=x; son[x][0]=y;
 55     pushup(y); pushup(x);
 56 }
 57 
 58 inline void splay(int x)
 59 {
 60     while(!isroot(x))
 61     {
 62         int y=fa[x];
 63         if(isroot(y))
 64         {
 65             if(son[y][0]==x) zig(x);
 66             else zag(x);
 67         }
 68         else
 69         {
 70             if(son[fa[y]][0]==y)
 71             {
 72                 if(son[y][0]==x) zig(y);
 73                 else zag(x);
 74                 zig(x);
 75             }
 76             else
 77             {
 78                 if(son[y][0]==x) zig(x);
 79                 else zag(y);
 80                 zag(x);
 81             }
 82         }
 83     }
 84 }
 85 
 86 inline void access(int x)
 87 {
 88     for(int y=0;x;y=x,x=fa[x])
 89     {
 90         splay(x);
 91         son[x][1]=y;
 92     }
 93 }
 94 
 95 inline void cut(int x,int y)
 96 {
 97     access(x); splay(x);
 98     fa[son[x][0]]=0;
 99     son[x][0]=0;
100     fa[x]=min(x+y,n+1);
101     access(x);
102 }
103 
104 inline void change(int x)
105 {
106     access(x); splay(x);
107     printf("%d\n",sum[son[x][0]]);
108 }
109 
110 inline void go()
111 {
112     int x,y;
113     scanf("%d",&m);
114     while(m--)
115     {
116         scanf("%d",&x);
117         if(x==1)
118         {
119             scanf("%d",&x); x++;
120             change(x);
121         }
122         else
123         {
124             scanf("%d%d",&x,&y);x++;
125             cut(x,y);
126         }
127     }
128 }
129 
130 int main()
131 {
132     read(),go();
133     return 0;
134 }

 

posted @ 2013-01-05 00:00  proverbs  阅读(224)  评论(0编辑  收藏  举报