POJ-3321-Apple Tree dfs序树状数组
具体题目是,POJ-3321,这里不给了;
数据先给了n;代表了一共有n个编号(对于n个结点);
大致题意是给一颗根节点为编号1的树,以及接下来的n-1条边(x,y) 根据discuss区描述这条边就是x to y,不用考虑y to x;(这不是重点)
再是m个操作(点修改and这个点的子树的结点个数查询);
3
1 2
1 3
3
Q 1
C 2
Q 1
dfs序 后 用树状数组或者线段树维护
vector< vector<int> >G(N);
注意这里我改成了这样建树,不然就TLE了
#include<iostream>
#include<vector>
#include<cstring>
#define rep(i,l,r) for(int i=l;i<r;i++)
#define Rep(i,l,r) for(int i=l;i<=r;i++)
#define rrep(i,l,r) for(int i=r;i>=l;i--)
#define lc rt<<1
#define lson l,m,rt<<1
#define rc rt<<1|1
#define rson m+1,r,rt<<1|1
#define mp make_pair
#define pb push_back
#define all(x) x.begin(),x.end()
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10;
int L[N],R[N],key;
bool noApple[N],vis[N];
vector< vector<int> > G(N);
int c[N];
int n;
int lbt(int x){return x&(-x);}
void update(int x,int v){while(x<=n){c[x]+=v;x+=lbt(x);}}
int query(int x){int ret=0;while(x>0){ret+=c[x];x-=lbt(x);}return ret;}
void dfs(int u){
vis[u]=true;
key++;
L[u]=key;
for(int i=0;i<G[u].size();i++){
int v=G[u][i];
if(!vis[v]){
dfs(v);
}
}
R[u]=key;
}
int main()
{
//freopen("in.txt","r",stdin);
//freopen("out.txt","w",stdout);
int q;
int kase=0;
while(~scanf("%d",&n)){
//printf("Case %d: ",++kase);
Rep(i,1,n)G[i].clear();
memset(noApple,false,sizeof noApple);
memset(vis,false,sizeof vis);
int x,y;
rep(i,0,n-1){scanf("%d%d",&x,&y);G[x].pb(y);G[y].pb(x);}
dfs(1);
Rep(i,1,n)update(i,1);
scanf("%d",&q);char op[10];
while(q--){
scanf("%s%d",op,&x);
if(op[0]=='Q') printf("%d\n",query(R[x])-query(L[x]-1));
else {update(L[x],noApple[x]?1:-1);noApple[x]=!noApple[x];}
}
}
return 0;
}