F - Assign the task HDU - 3974
dfs序线段树
把树形结构变成线性区间结构,树的向下传值变成了这个节点能覆盖的区间的修改。
线段树代码是真的难调,一点小bug就是找不出来,卡了两天。
1 #include <iostream> 2 #include <cstring> 3 4 using namespace std; 5 #define lson l,m,rt<<1 6 #define rson m+1,r,rt<<1|1 7 8 const int maxn=5e5+5; 9 10 //建初始图 11 struct edge 12 { 13 int v;int nex; 14 }e[maxn]; 15 int head[maxn]; 16 int tot; 17 void addedge(int u,int v){ 18 e[tot].v=v; 19 e[tot].nex=head[u]; 20 head[u]=tot++; 21 } 22 23 //求dfs序 24 int start[maxn],endss[maxn],ru[maxn]; 25 int cnt; 26 void dfs(int u){ 27 ++cnt; 28 start[u]=cnt; 29 for(int i=head[u];i!=-1;i=e[i].nex){ 30 dfs(e[i].v); 31 } 32 endss[u]=cnt; 33 } 34 35 //初始化 36 void init(){ 37 cnt=0;tot=0; 38 memset(head,-1,sizeof(head)); 39 memset(ru,0,sizeof(ru)); 40 } 41 42 //线段树 43 int tree[maxn<<4],f[maxn<<4]; 44 45 void Pushup(int rt){ 46 int cntl=tree[rt<<1]; 47 int cnt2=tree[rt<<1|1]; 48 if(cntl==cnt2) tree[rt]=cntl; 49 else tree[rt]=-2; 50 51 } 52 53 void Pushdown(int rt){ 54 if(f[rt]!=-1){ 55 tree[rt<<1]=f[rt]; 56 tree[rt<<1|1]=f[rt]; 57 f[rt<<1]=f[rt]; 58 f[rt<<1|1]=f[rt]; 59 f[rt]=-1; 60 } 61 } 62 63 void build(int l,int r,int rt){ 64 if(l==r) 65 { 66 f[rt]=-1; 67 tree[rt]=-1; 68 return; 69 } 70 tree[rt]=-1; 71 f[rt]=-1; 72 int m=(l+r)>>1; 73 build(lson); 74 build(rson); 75 } 76 77 void update(int y,int L,int R,int l,int r,int rt){ 78 if(L<=l&&r<=R){ 79 tree[rt]=y; 80 f[rt]=y; 81 return ; 82 } 83 Pushdown(rt); 84 int m=(l+r)>>1; 85 if(L<=m) update(y,L,R,lson); 86 if(R>m) update(y,L,R,rson); 87 Pushup(rt); 88 } 89 90 int query(int x,int l,int r,int rt){ 91 if(x<=r&&x>=l&&tree[rt]!=-2) 92 { 93 return tree[rt]; 94 } 95 Pushdown(rt); 96 int m=(l+r)>>1; 97 if(x<=m) return query(x,lson); 98 else return query(x,rson); 99 } 100 101 int main(){ 102 std::ios::sync_with_stdio(false); 103 int T;cin>>T; 104 for(int t=1;t<=T;t++){ 105 init(); 106 int n;cin>>n; 107 cout <<"Case #"<<t<<":\n"; 108 for(int i=1;i<n;i++) 109 { 110 int u,v;cin>>u>>v; 111 //cout <<i<<endl; 112 addedge(v,u); 113 ru[u]=1; 114 } 115 for(int i=1;i<=n;i++){ 116 if(!ru[i]){ 117 //cout <<i<<endl; 118 dfs(i); 119 break; 120 } 121 } 122 /*for(int i=1;i<=n;i++) 123 { 124 cout <<i<<"=="<<start[i]<<" "<<endss[i]<<endl; 125 } 126 cout <<endl;*/ 127 build(1,cnt,1); 128 //for(int i=1;i<=5;i++) cout <<tree[i]<<" "; 129 int m;cin>>m; 130 for(int i=1;i<=m;i++){ 131 //cout <<"tree="<<tree[3]<<endl; 132 char c;cin>>c; 133 int a,b; 134 if(c=='C') 135 { 136 cin>>a; 137 cout <<query(start[a],1,n,1)<<"\n"; 138 } 139 else 140 { 141 cin>>a>>b; 142 update(b,start[a],endss[a],1,n,1); 143 } 144 } 145 } 146 return 0; 147 }