记录编号 384267 评测结果 AAAAA
题目名称 2281.[HZOI 2015]白黑树 最终得分 100
用户昵称 AntiLeaf 是否通过 通过
代码语言 C++ 运行时间 0.293 s
提交时间 2017-03-17 20:50:38 内存使用 21.10 MiB
显示代码纯文本
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<vector>
using namespace std;
const int maxn=200010;
void dfs(int);
void add(int,int);
int query(int);
vector<int>G[maxn];
int f[maxn][20],d[maxn],dfn[maxn],finish[maxn],tim=0,c[maxn];
bool col[maxn]={false};
char op;
int n,m,lgn=0,black=0,x,y;
int main(){
	freopen("C_Tree.in","r",stdin);
	freopen("C_Tree.out","w",stdout);
	scanf("%d%d",&n,&m);
	for(int i=1;i<n;i++){
		scanf("%d%d",&x,&y);
		G[x].push_back(y);
		G[y].push_back(x);
	}
	dfs(1);
	for(int j=1;j<=lgn;j++)for(int i=1;i<=n;i++)f[i][j]=f[f[i][j-1]][j-1];
	while(m--){
		scanf(" %c%d",&op,&x);
		if(op=='M'){
			add(dfn[x],col[x]?-1:1);
			black+=(col[x]?-1:1);
			col[x]^=true;
		}
		else{
			if(!black)printf("-1\n");
			else if(query(finish[x])-query(dfn[x]-1)==black)printf("%d\n",x);
			else{
				for(int i=lgn;i>=0;i--)if(f[x][i]&&query(finish[f[x][i]])-query(dfn[f[x][i]]-1)<black)x=f[x][i];
				printf("%d\n",f[x][0]);
			}
		}
	}
	return 0;
}
void dfs(int x){
	dfn[x]=++tim;
	d[x]=d[f[x][0]]+1;
	while((1<<lgn)<d[x])lgn++;
	for(int i=0;i<(int)G[x].size();i++)if(G[x][i]!=f[x][0]){
		f[G[x][i]][0]=x;
		dfs(G[x][i]);
	}
	finish[x]=tim;
}
void add(int x,int d){
	while(x<=n){
		c[x]+=d;
		x+=x&-x;
	}
}
int query(int x){
	int ans=0;
	while(x){
		ans+=c[x];
		x&=x-1;
	}
	return ans;
}