[CF600E] Lomsat gelral-- tree heuristic merge

(Face questions from luogu)

Translation of the meaning of problems

A tree with n nodes, each node is a color, a number for each color, the color number of up request for each tree and subtree.

ci <= n <= 1e5

 

  The combined bare tree heuristic problem. When statistics first sweep again to get the maximum number of occurrences, then sweep it again to see the number of occurrences and mxCnt which equal color. To shoving the bool array are also labeled with a false note bool array sentenced to heavy, empty the contribution son when Light.

Code:

  1. #include <iostream>  
  2. #include <cstdio>  
  3. #include <cctype>  
  4. #define maxn 100010  
  5. using namespace std;  
  6. template <typename T>  
  7. void read(T &x) {  
  8.     x = 0;  
  9.     char ch = getchar();  
  10.     while (!isdigit(ch))  
  11.         ch = getchar();  
  12.     while (isdigit(ch))  
  13.         x = x * 10 + (ch ^ 48), ch = getchar();  
  14. }  
  15. int n;  
  16. int head[maxn], top;    
  17. struct E {    
  18.     int to, nxt;    
  19. } edge[maxn << 1];    
  20. inline void insert(int u, int v) {    
  21.     edge[++top] = (E) {v, head[u]};    
  22.     head[u] = top;    
  23. }    
  24. int son[maxn], size[maxn];  
  25. long long ans[maxn];  
  26. void dfs1(int u, int pre) {  
  27.     size[u] = 1;  
  28.     for (int i = head[u]; i; i = edge[i].nxt) {  
  29.         int v = edge[i].to;  
  30.         if (v == pre) continue;  
  31.         dfs1 (v, u);  
  32.         size[u] += size[v];  
  33.         if (size[v] > size[son[u]])  
  34.             son[u] = v;  
  35.     }  
  36.     return;  
  37. }  
  38. int color[maxn], cnt[maxn], sum;  
  39. int curSon, mxCnt;  
  40. bool vis[maxn];  
  41. void calc(int u, int pre, bool op) {  
  42.     op ? (++cnt[color[u]], mxCnt = max(mxCnt, cnt[color[u]])) : (--cnt[color[u]], vis[color[u]] = false);  
  43.     for (int i = head[u]; i; i = edge[i].nxt) {  
  44.         int v = edge[i].to;  
  45.         if (in the || == == the curson)  
  46.             continue;  
  47.         calc (v, u, at);  
  48.     }  
  49. }  
  50. void stats(int u, int pre) {  
  51.     if (cnt[color[u]] == mxCnt && !vis[color[u]])  
  52.         sum += color[u], vis[color[u]] = true;  
  53.     for (int i = head[u]; i; i = edge[i].nxt) {  
  54.         int v = edge[i].to;  
  55.         if (v != pre)  
  56.             stats(v, u);  
  57.     }  
  58.     return;  
  59. }  
  60. void dsu(int u, int pre, bool op) {  
  61.     for (int i = head[u]; i; i = edge[i].nxt) {  
  62.         int v = edge[i].to;  
  63.         if (v == pre || v == son[u])      
  64.             continue;  
  65.         dsu (v, u, 0);  
  66.     }  
  67.     if (son[u])  
  68.         DSU (son [u], u, 1) = curson son [in];  
  69.     mxCnt = 0;  
  70.     calc (in, for, 1);  
  71.     stats(u, pre);  
  72.     ans[u] = sum;  
  73.     curSon = 0;  
  74.     if (! on) {  
  75.         sum = 0;  
  76.         calc (in, on, 0);  
  77.     }  
  78. }  
  79. int main () {  
  80.     read(n);  
  81.     for (int i = 1; i <= n; ++i)  
  82.         read(color[i]);  
  83.     you and, v;  
  84.     for (int i = 1; i < n; ++i) {  
  85.         read(u), read(v);  
  86.         insert(v, u), insert(u, v);  
  87.     }  
  88.     dfs1 (1, 0);  
  89.     dsu (1, 0, 1);  
  90.     for (int i = 1; i <= n; ++i)  
  91.         printf("%I64d ", ans[i]);  
  92.     return 0;  
  93. }  

   When this problem cf pay just explode ......

Guess you like

Origin www.cnblogs.com/TY02/p/11323015.html