HDU - 3974 Assign the task
题 意:一个公司,每个员工都只有一个直接的上司,上司的上司是我的上司,下属的下属是我的下属。现在公司分配任务,T x y。将任务y分配给x以及他的下属。也就是说,x和他的下属同时收到任务。当x和他的下属同时收到任务时,他们会停下手中的工作去做任务y。现在m次操作。C x.询问x现在手中的任务.T x y:将任务y分配给x以及他的下
数据范围:
T<=50
N<=50000
X<=n
y<=1e9
输入样例:
1
5
4 3
3 2
1 3
5 2
5
C 3
T 2 1
C 3
T 3 2
C 3
输出样例:
Case #1:
-1
1
2
dfs序列.
思 路:dfs序列记录好它和它子节点的开始和结束编号,加线段树维护。
2是[1,5],5是[2,2],3是[3,5],1是[4,4],4是[5,5]用一个start数组,一个end数组去储存就好,然后用线段树去维护.
收 获:学会了用线段树去维护dfs序列
#include<bits/stdc++.h>
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
using namespace std;
const int maxn = 5e4+5;
struct node{
int to,next;
}edge[maxn];
int head[maxn],cnt,tot;
bool vis[maxn];
int start[maxn],en[maxn];
int sum[maxn<<2],lazy[maxn<<2];
int n,m;
void addedge(int u,int v){
edge[tot].to = v;
edge[tot].next = head[u];
head[u] = tot++;
}
void init(){
memset(head,-1,sizeof(head));
memset(vis,false,sizeof(vis));
cnt = 0;
tot = 0;
}
void dfs(int u){
++cnt;
start[u] = cnt;
for(int i=head[u];i!=-1;i=edge[i].next){
int to = edge[i].to;
dfs(to);
}
en[u] = cnt;
}
void build(int l,int r,int rt){
sum[rt] = -1;
lazy[rt] = 0;
if(l == r){
return;
}
int m = (l+r)>>1;
build(lson);
build(rson);
}
void PushDown(int rt){
if(lazy[rt]){
lazy[rt<<1] = lazy[rt];
lazy[rt<<1|1] = lazy[rt];
sum[rt<<1] = sum[rt];
sum[rt<<1|1] = sum[rt];
lazy[rt] = 0;
}
}
void update(int L,int R,int x,int l,int r,int rt){
if(L<=l && r<=R){
sum[rt] = x;
lazy[rt] = 1;
return ;
}
PushDown(rt);
int m = (l+r)>>1;
if(L<=m) update(L,R,x,lson);
if(R > m) update(L,R,x,rson);
}
int query(int x,int l,int r,int rt){
if(l == r){
return sum[rt];
}
PushDown(rt);
int m = (l+r)>>1;
if(x<=m) query(x,lson);
else query(x,rson);
}
int main(){
int t;
int Kase = 1;
scanf("%d",&t);
while(t--){
printf("Case #%d:\n",Kase++);
init();
scanf("%d",&n);
for(int i=1;i<=n-1;i++){
int u,v;
scanf("%d %d",&v,&u);
addedge(u,v);
vis[v] = true;
}
for(int i=1;i<=n;i++){
if(!vis[i]){
dfs(i);
break;
}
}
build(1,cnt,1);
scanf("%d",&m);
char s[10];int l,r;
for(int i=1;i<=m;i++){
scanf("%s",s);
if(s[0] == 'C'){
scanf("%d",&l);
int ans = query(start[l],1,n,1);
printf("%d\n",ans);
}else{
scanf("%d %d",&l,&r);
update(start[l],en[l],r,1,n,1);
}
}
}
return 0;
}
/*
2
6 2 4
*/