3321 Apple Tree 树状数组

LIANJIE:http://poj.org/problem?id=3321

给你一个多叉树,每个叉和叶子节点有一颗苹果。然后给你两个操作,一个是给你C清除某节点上的苹果或者添加(此节点上有苹果则清除没苹果就添加)q询问这个节点的子树上有多少个苹果。

直接dfs遍历一遍,每个节点给一个时间戳,记录一下遍历玩这个节点是的始终时间戳,直接对时间戳进行询问即可。

  1 #include <stdio.h>
  2 #include <string.h>
  3 #include <iostream>
  4 #include <algorithm>
  5 #include <stdlib.h>
  6 #include <vector>
  7 #include <queue>
  8 #include <stack>
  9 #define loop(s,i,n) for(i = s;i < n;i++)
 10 #define cl(a,b) memset(a,b,sizeof(a))
 11 #define lowbit(x) x&-x
 12 
 13 using namespace std;
 14 const int maxn = 100005;
 15 
 16 struct node
 17 {
 18     int u,v,w,next;
 19 }edges[maxn*2];
 20 int head[maxn];
 21 bool vis[maxn];
 22 int dfsclock,n,cnt,pt[maxn],c[maxn];
 23 struct time
 24 {
 25     int s,e;
 26 }a[maxn];
 27 void init()
 28 {
 29     int i;
 30     for(i = 0;i <= n;i++)
 31     head[i] = -1,vis[i] = 0,c[i] = 0;
 32     cnt = dfsclock = 0;
 33 }
 34 int sum(int x)
 35 {
 36     int ret = 0;
 37     while(x > 0)
 38     {
 39         ret+=c[x];
 40         x-=lowbit(x);
 41     }
 42     return ret;
 43 }
 44 void add(int x,int d)
 45 {
 46     while(x <= n)
 47     {
 48         c[x]+= d;
 49         x+=lowbit(x);
 50     }
 51 }
 52 void addedge(int u,int v,int w)
 53 {
 54     int i;
 55     edges[cnt].u = u;
 56     edges[cnt].v = v;
 57     edges[cnt].w = w;
 58     edges[cnt].next = head[u];
 59     head[u] = cnt;
 60     cnt++;
 61 }
 62 void dfs(int u)
 63 {
 64     dfsclock++;
 65     vis[u] = 1;
 66     a[u].s = dfsclock;
 67     int i;
 68     for(i = head[u];i != -1;i = edges[i].next)
 69     {
 70         int v;
 71         v = edges[i].v;
 72         if(!vis[v])
 73         {
 74             dfs(v);
 75         }
 76     }
 77     a[u].e = dfsclock;
 78 
 79 }
 80 int main()
 81 {
 82     int q;
 83     while(~scanf("%d",&n))
 84     {
 85 
 86         int i;
 87         init();
 88         //memset(head,-1,sizeof(head));
 89         //cnt = 0;
 90         loop(0,i,n-1)
 91         {
 92             int u,v;
 93             scanf("%d %d",&u,&v);
 94             addedge(u,v,1);
 95             addedge(v,u,1);
 96         }
 97 
 98         dfs(1);
 99 
100         for(i = 1;i <= n;i++)
101         add(i,1);
102         scanf("%d",&q);
103         while(q--)
104         {
105             char s[2];
106             int num;
107             scanf("%s%d",s,&num);
108             if(s[0] == 'Q')
109             {
110                 printf("%d
",sum(a[num].e)-sum(a[num].s-1));
111             }
112             else
113             {
114                 int leap;
115                 leap = sum(a[num].s)-sum(a[num].s-1);
116               //  cout<<leap<<"**"<<endl;
117                 if(leap)
118                 add(a[num].s,-1);
119                 else
120                 add(a[num].s,1);
121             }
122         }
123 
124     }
125     return 0;
126 }
View Code
原文地址:https://www.cnblogs.com/0803yijia/p/3296849.html