Topic links: https://ac.nowcoder.com/acm/contest/3566/B
Ideas: a road can be divided into the left and right portions of FIG.
l_ci, l_peo, r_ci, r_peo, w respectively, left the city and the number of persons, the right number and the number of cities, the cost of the road.
We know that people go to the left r_ci cities on the right, the right of people to go l_ci cities left,
Then the cost of the path is cost = 2 * w * (l_ci * r_peo + r_ci * l_peo); (note that back and forth).
We can use the topological sort to derive an edge around the city and the number of cases.
1 #include <iostream> 2 #include <cstdio> 3 #include <algorithm> 4 #include <queue> 5 using namespace std; 6 typedef long long ll; 7 8 const int N = (int)2e5+100; 9 struct node{ 10 int to,nxt; 11 }e[N<<1]; 12 struct Info{ 13 int ci,peo; 14 Info(){ci = peo = 0;} 15 } info [N]; 16 int A [N], W is [N], du [N], head [N]; // number, toll, degrees . 17 BOOL VIS [N]; 18 is int n-, U , V, W, TOT; LL sum_peo; . 19 20 is inline void the Add ( int U, int V) { 21 is E [TOT] .to = V; E [TOT] .nxt head = [U]; head [U] = ++ TOT ; 22 is E [TOT] .to = U; E [TOT] = .nxt head [V]; head [V] TOT = ++ ; 23 is } 24 25 void top_sort () { 26 is // degree of pressure into a 27 Queue < int >que; 28 for ( int I = . 1 ; I <= n-; ++ I) { 29 IF (du [I] == . 1 ) { 30 VIS [I] = . 1 ; 31 is que.push (I); 32 } 33 is } 34 is 35 the while (! {que.empty ()) 36 int now = que.front (); que.pop (); 37 [ // add their city case 38 is info [now] + = .ci . 1 ; 39 info [now] + = .peo A [now]; 40 for( Int O = head [now]; ~ O; O = E [O] .nxt) { 41 is int to = E [O] .to; 42 is IF (! {VIS [to]) 43 is // pass their city the case 44 is info [to] + = .ci info [now] .ci; 45 info [to] + = .peo info [now] .peo; 46 is IF (--du [to] == . 1 ) { 47 VIS [ to] = . 1 ; 48 que.push (to); 49 } 50 } 51 is } 52 is } 53 } 54 55 void show_info(){ 56 for(int i = 1;i <= n; ++i){ 57 printf("now = %d city = %d people = %d\n",i,info[i].ci,info[i].peo); 58 } 59 } 60 61 inline ll cost(Info& u,int i){ 62 Info v; 63 v.ci = n-u.ci; 64 v.peo = sum_peo - u.peo; 65 // printf("u.c = %d v.c = %d u.p = %d v.p = %d W = %d\n",u.ci,v.ci,u.peo,v.peo,W[i]); 66 return (ll)2*W[i]*((ll)u.ci*v.peo+(ll)v.ci*u.peo); 67 } 68 69 int main(){ 70 71 scanf("%d",&n); 72 for(int i = 0; i <= n; ++i) head[i] = -1; tot = 0; 73 for(int i = 1; i <= n; ++i){ 74 scanf("%d",A+i); 75 sum_peo += A[i]; 76 } 77 for(int i = 1; i < n; ++i){ 78 scanf("%d%d%d",&u,&v,W+i); 79 add(u,v); 80 ++du[u]; ++du[v];//无向边 81 } 82 top_sort(); 83 //show_info(); 84 for(int i = 0; i < 2*(n-1); i+=2 ) { 85 // we always selected from a small number of cities edge drawn aside and the other side of the city where the number 86 int X = info [E [I] .to] .ci <info [E [I ^ . 1 ?] .to] .ci E [I] .to: E [I ^ . 1 ] .to; 87 // the printf ( "City D =% \ n-", X); 88 the printf ( " % LLD \ n- " , cost (info [X], . 1 + (I >> . 1 ))); 89 } 90 91 is return 0 ; 92 }