Counting Offspring
Time Limit: 15000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Problem Description
You are given a tree, it’s root is p, and the node is numbered from 1 to n. Now define f(i) as the number of nodes whose number is less than i in all the succeeding nodes of node i. Now we need to calculate f(i) for any possible i.
Input
Multiple cases (no more than 10), for each case:
The first line contains two integers n (0<n<=10^5) and p, representing this tree has n nodes, its root is p.
Following n-1 lines, each line has two integers, representing an edge in this tree.
The input terminates with two zeros.
The first line contains two integers n (0<n<=10^5) and p, representing this tree has n nodes, its root is p.
Following n-1 lines, each line has two integers, representing an edge in this tree.
The input terminates with two zeros.
Output
For each test case, output n integer in one line representing f(1), f(2) … f(n), separated by a space.
Sample Input
15 7
7 10
7 1
7 9
7 3
7 4
10 14
14 2
14 13
9 11
9 6
6 5
6 8
3 15
3 12
0 0
Sample Output
0 0 0 0 0 1 6 0 3 1 0 0 0 2 0
Author
bnugong
Source
树状数组,父亲节点i 时,统计比 i 小的个数 ,递归回退到 i 时,再次统计比 i 小的个数。
#include <iostream> #include <stdio.h> #include <string.h> #include <string> #include <map> #include <vector> #include <set> #include <algorithm> #include <vector> #include <stack> #include <math.h> #include <stdlib.h> #include <fstream> #include <queue> #define Max(a,b) ((a)>(b)?(a):(b)) #define Min(a,b) ((a)<(b)?(a):(b)) #pragma comment(linker, "/STACK:16777216") using namespace std; typedef long long LL ; const int size=1000008 ; struct Edge{ int v ; int next ; }; Edge edge[size*2] ; int id ; int C[size] ; int vec[size] ; int ans[size] ; bool visited[size] ; struct Me{ int N ; int root ; Me(){} ; Me(int n,int r):N(n),root(r){ fill(C,C+1+N,0) ; id=0 ; fill(vec,vec+1+N,-1) ; fill(visited,visited+1+N,0) ; fill(ans,ans+1+N,0) ; }; inline void add_edge(int u ,int v){ edge[id].v=v ; edge[id].next=vec[u] ; vec[u]=id++ ; } inline int lowbit(int x){ return x&(-x) ; } void insert(int id ,int x){ while(id<=N){ C[id]+=x ; id+=lowbit(id) ; } } int get_sum(int id){ int sum=0 ; while(id>=1){ sum+=C[id] ; id-=lowbit(id) ; } return sum ; } void dfs(int now){ visited[now]=1 ; int less_sum=get_sum(now-1) ; insert(now,1) ; for(int e=vec[now];e!=-1;e=edge[e].next){ int son=edge[e].v ; if(visited[son]) continue ; dfs(son) ; } ans[now]=get_sum(now-1)-less_sum ; } void gao(){ int u ,v ; for(int i=1;i<N;i++){ scanf("%d%d",&u,&v) ; add_edge(u,v) ; add_edge(v,u) ; } dfs(root) ; printf("%d",ans[1]) ; for(int i=2;i<=N;i++) printf(" %d",ans[i]) ; puts("") ; } }; int main(){ int n , p ; while(scanf("%d%d",&n,&p)){ if(n==0&&p==0) break ; Me me(n,p) ; me.gao() ; } return 0; }