zoj 3686 A Simple Tree Problem
2013-04-01 16:19
337 查看
题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3686
题目大意:
一棵树有n个结点(1<=N<=100000),根为1,每个结点有一个标签,初始值为0.
现在有2种操作
o操作:(o,x)对结点x及其所有子孙结点的标签值取反(和1异或)。
q操作:(q,x)输出结点x及其所以子孙结点的标签值为1的个数。
操作次数为m次(1<=M<=10000)。
题目思路:
从根开始中序遍历每一个结点,给每一个结点按照遍历顺序重新编号(beg)。
这样子可以使得重新编号的结点,根及其连接的子树的结点是连续的,这样我们就可以操作时区间更新和区间询问了。
并且遍历时记录下某根子树中最大的结点编号(end),这样我们更新或询问某结点及其子树的范围即
[ beg[x] , end[x] ]。
代码:
题目大意:
一棵树有n个结点(1<=N<=100000),根为1,每个结点有一个标签,初始值为0.
现在有2种操作
o操作:(o,x)对结点x及其所有子孙结点的标签值取反(和1异或)。
q操作:(q,x)输出结点x及其所以子孙结点的标签值为1的个数。
操作次数为m次(1<=M<=10000)。
题目思路:
从根开始中序遍历每一个结点,给每一个结点按照遍历顺序重新编号(beg)。
这样子可以使得重新编号的结点,根及其连接的子树的结点是连续的,这样我们就可以操作时区间更新和区间询问了。
并且遍历时记录下某根子树中最大的结点编号(end),这样我们更新或询问某结点及其子树的范围即
[ beg[x] , end[x] ]。
代码:
#include <stdlib.h> #include <string.h> #include <stdio.h> #include <ctype.h> #include <math.h> #include <stack> #include <queue> #include <map> #include <set> #include <vector> #include <string> #include <iostream> #include <algorithm> using namespace std; #define ll __int64 #define ls rt<<1 #define rs ls|1 #define lson l,mid,ls #define rson mid+1,r,rs #define middle (l+r)>>1 #define clr_all(x,c) memset(x,c,sizeof(x)) #define clr(x,c,n) memset(x,c,sizeof(x[0])*(n+1)) #define eps (1e-8) #define MOD 1000000007 #define INF 0x3f3f3f3f #define PI (acos(-1.0)) #pragma comment(linker, "/STACK:102400000,102400000") template <class T> T _max(T x,T y){return x>y? x:y;} template <class T> T _min(T x,T y){return x<y? x:y;} template <class T> T _abs(T x){return (x < 0)? -x:x;} template <class T> T _mod(T x,T y){return (x > 0)? x%y:((x%y)+y)%y;} template <class T> void _swap(T &x,T &y){T t=x;x=y;y=t;} template <class T> void getmax(T& x,T y){x=(y > x)? y:x;} template <class T> void getmin(T& x,T y){x=(x<0 || y<x)? y:x;} int TS,cas=1; const int M=100000+5; int n,m; struct node{ int beg,end; }mp[M]; int fa[M],nxt[M],vec[M],tot; void dfs(int rt){ mp[rt].beg=++tot; for(int i=fa[rt];i!=-1;i=nxt[i]) dfs(vec[i]); mp[rt].end=tot; } int cov[M<<2],sum[M<<2]; void build(int l,int r,int rt){ cov[rt]=sum[rt]=0; if(l==r) return; int mid=middle; build(lson),build(rson); } void pushDown(int l,int mid,int r,int rt){ if(!cov[rt]) return; sum[ls]=(mid-l+1)-sum[ls],cov[ls]^=1; sum[rs]=(r-mid)-sum[rs],cov[rs]^=1; cov[rt]=0; } void pushUp(int rt){ sum[rt]=sum[ls]+sum[rs]; } void update(int l,int r,int rt,int L,int R){ if(L<=l && r<=R){ sum[rt]=(r-l+1)-sum[rt]; cov[rt]^=1; return; } int mid=middle; pushDown(l,mid,r,rt); if(R<=mid) update(lson,L,R); else if(mid<L) update(rson,L,R); else update(lson,L,mid),update(rson,mid+1,R); pushUp(rt); } int query(int l,int r,int rt,int L,int R){ if(L<=l && r<=R) return sum[rt]; int mid=middle; pushDown(l,mid,r,rt); if(R<=mid) return query(lson,L,R); else if(mid<L) return query(rson,L,R); else return query(lson,L,mid)+query(rson,mid+1,R); } void run(){ int i,j; clr(fa,-1,n+1); tot=0; for(i=2;i<=n;i++){ scanf("%d",&j); nxt[tot]=fa[j],vec[tot]=i,fa[j]=tot++; } tot=0; dfs(1); build(1,n,1); while(m--){ char op[3]; scanf("%s%d",op,&j); if(op[0] == 'o') update(1,n,1,mp[j].beg,mp[j].end); else printf("%d\n",query(1,n,1,mp[j].beg,mp[j].end)); } puts(""); } void preSof(){ } int main(){ //freopen("input.txt","r",stdin); //freopen("output.txt","w",stdout); preSof(); //run(); while((~scanf("%d%d",&n,&m))) run(); //for(scanf("%d",&TS);cas<=TS;cas++) run(); return 0; }
相关文章推荐
- ZOJ3686 A Simple Tree Problem
- zoj 3686 A Simple Tree Problem
- ZOJ 3686 A Simple Tree Problem
- ZOJ 3686 A Simple Tree Problem(线段树)
- zoj 3686 A Simple Tree Problem(dfs+线段树)
- ZOJ 3686 A Simple Tree Problem(将对树的操作转化成区间=>线段树)
- ZOJ 3686 A Simple Tree Problem (线段树)
- ZOJ 3686 A Simple Tree Problem(树转线段树+线段树区间更新)
- ZOJ 3686 : A Simple Tree Problem
- zoj3686 A Simple Tree Problem
- ZOJ 3686 A Simple Tree Problem (线段树)
- ZOJ_3686_A Simple Tree Problem(线段树成端更新)
- ZOJ 3686 A Simple Tree Problem(线段树)
- ZOJ 3686 A A Simple Tree Problem
- zoj 3686 A Simple Tree Problem (经典,利用dfs序维护树)
- ZOJ 3686 A Simple Tree Problem
- zoj 3686 A Simple Tree Problem (线段树)
- ZOJ 3686 A Simple Tree Problem(线段树)
- ZOJ 3686 A Simple Tree Problem
- ZOJ-3686 A Simple Tree Problem 线段树