题面:无
题解:无
代码:
1 #include<cstdio> 2 #include<cstring> 3 #include<iostream> 4 #include<algorithm> 5 using namespace std; 6 const int maxn=(1e5)+50; 7 int N,T,u,v,num_edge,edge_head[maxn],lsh_cnt,belong[maxn],tr[maxn],Ans[maxn]; 8 //记住树状数组里不可以塞0 9 //tr中的数会在回溯时删掉,所以不用清空tr 10 struct Edge{int to,nx;}edge[maxn<<1]; 11 inline void Add_edge(int from,int to){ 12 edge[++num_edge].nx=edge_head[from]; 13 edge[num_edge].to=to; 14 edge_head[from]=num_edge; 15 return; 16 } 17 struct Nd{int yw,w,id;}nd[maxn]; 18 inline bool cmp(const Nd&a,const Nd&b){return a.yw<b.yw;} 19 inline void Add(int s,int x){ 20 for(int i=s;i>0;i-=i&(-i))tr[i]+=x; 21 return; 22 } 23 inline int Find(int s){ 24 int ans=0; 25 for(int i=s;i<=lsh_cnt;i+=i&(-i))ans+=tr[i]; 26 return ans; 27 } 28 inline void Dfs(int x,int f){ 29 for(int i=edge_head[x];i;i=edge[i].nx){ 30 int y=edge[i].to; 31 if(y!=f){ 32 Add(nd[belong[x]].w,1); 33 Dfs(y,x); 34 Add(nd[belong[x]].w,-1); 35 } 36 } 37 Ans[x]=Find(nd[belong[x]].w+1); 38 return; 39 } 40 int main(){ 41 scanf("%d",&T); 42 while(T--){ 43 num_edge=lsh_cnt=0; 44 memset(edge_head,0,sizeof(edge_head)); 45 scanf("%d",&N); 46 for(int i=1;i<N;i++){ 47 scanf("%d%d",&u,&v); 48 Add_edge(u,v); 49 Add_edge(v,u); 50 } 51 for(int i=1;i<=N;i++){ 52 scanf("%d",&nd[i].yw); 53 nd[i].id=i; 54 } 55 sort(nd+1,nd+N+1,cmp); 56 nd[1].w=++lsh_cnt; 57 belong[nd[1].id]=1; 58 for(int i=2;i<=N;i++){ 59 if(nd[i].yw!=nd[i-1].yw)lsh_cnt++; 60 nd[i].w=lsh_cnt; 61 belong[nd[i].id]=i; 62 } 63 Dfs(1,0); 64 for(int i=1;i<=N;i++)printf("%d ",Ans[i]); 65 } 66 return 0; 67 }
By:AlenaNuna