简单树刨+线段树模板 877E

#include<bits/stdc++.h>
using namespace std;
const int maxn=200008;
struct fuck{
	int v,next;
}edge[maxn];
int tol;
int head[maxn];
void init()
{
	tol=0;
	memset(head,-1,sizeof(head));
}
void addedge(int u,int v)
{
	edge[tol].v=v;
	edge[tol].next=head[u];
	head[u]=tol++;
}
int li[maxn],ri[maxn];
int tim;
int w[maxn];
int b[maxn];
void dfs(int u)
{
	li[u]=++tim;
	b[tim]=w[u];
	for(int i=head[u];i!=-1;i=edge[i].next)
	{
		int v=edge[i].v;
		dfs(v);
	}
	ri[u]=tim;
}
int lazy[maxn<<2],a[maxn<<2];
void build(int x,int y,int c)
{
	lazy[c]=0;
	if(x==y)
	{
		a[c]=b[x];
		return;
	}
	int mid=(x+y)>>1;
	build(x,mid,c<<1);
	build(mid+1,y,c<<1|1);
	a[c]=a[c<<1]+a[c<<1|1];
}
void pushdown(int x,int y,int c)
{
	if(lazy[c]){
		int mid=(x+y)>>1;
		a[c<<1]=mid-x+1-a[c<<1];
		a[c<<1|1]=y-mid-a[c<<1|1];
		lazy[c<<1]=lazy[c<<1]^1;
		lazy[c<<1|1]=lazy[c<<1|1]^1;
		lazy[c]=0;
	}
}
void update(int sx,int sy,int x,int y,int c)
{
	if(sx<=x&&y<=sy)
	{
		lazy[c]=lazy[c]^1;
		a[c]=y-x+1-a[c];
		return;
	}
	pushdown(x,y,c);
	int mid=(x+y)>>1;
	if(sx<=mid)	update(sx,sy,x,mid,c<<1);
	if(sy>mid)	update(sx,sy,mid+1,y,c<<1|1);
	a[c]=a[c<<1]+a[c<<1|1];
}	
int query(int sx,int sy,int x,int y,int c)
{
	if(sx<=x&&y<=sy)
	{
		return a[c];
	}
	pushdown(x,y,c);
	int mid=(x+y)>>1;
	int sum=0;
	if(sx<=mid)	sum+=query(sx,sy,x,mid,c<<1);
	if(sy>mid)	sum+=query(sx,sy,mid+1,y,c<<1|1);
	return sum;
}
int main()
{
	int n;
	int u,v;
	while(scanf("%d",&n)==1)
	{
		init();
		for(int i=2;i<=n;i++)
		{
			scanf("%d",&u);
			addedge(u,i);
		}
		for(int i=1;i<=n;i++)
			scanf("%d",&w[i]);
		tim=0;dfs(1);
		build(1,tim,1);
		int q;
		scanf("%d",&q);
		while(q--)
		{
			char s[18];
			scanf("%s",s);
			scanf("%d",&u);
			if(s[0]=='g'){
				int shit=query(li[u],ri[u],1,tim,1);
				printf("%d
",shit);
			}
			else{
				update(li[u],ri[u],1,tim,1);
			}
		}
	}
	return 0;
}

  

原文地址:https://www.cnblogs.com/bitch1319453/p/7729192.html