Advertisement
Guest User

Untitled

a guest
Mar 30th, 2022
305
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.67 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int inf = 1e9 + 5, nmax = 1e5 + 5, nbit = 18;
  4. int n;
  5. vector< int > g[nmax];
  6. namespace CentroidDecompLmfao {
  7. namespace AINT {
  8. int aint[nmax * 4];
  9. void erase(int poz, int node = 1, int cl = 1, int cr = n) {
  10. if(cl == cr) {
  11. aint[node] = inf;
  12. return;
  13. }
  14. int mid = cl + cr >> 1;
  15. if(poz <= mid)
  16. erase(poz, 2 * node, cl, mid);
  17. else
  18. erase(poz, 2 * node + 1, mid + 1, cr);
  19. aint[node] = min(aint[2 * node], aint[2 * node + 1]);
  20. }
  21. int _query(int l, int r, int node = 1, int cl = 1, int cr = n) {
  22. if(l <= cl && cr <= r)
  23. return aint[node];
  24. if(r < cl || cr < l)
  25. return inf;
  26. int mid = cl + cr >> 1;
  27. return min(_query(l, r, 2 * node, cl, mid), _query(l, r, 2 * node + 1, mid + 1, cr));
  28. }
  29. int construct(int *p, int node = 1, int cl = 1, int cr = n) {
  30. if(cl == cr)
  31. return aint[node] = p[cl];
  32. int mid = cl + cr >> 1;
  33. return aint[node] = min(construct(p, 2 * node, cl, mid), construct(p, 2 * node + 1, mid + 1, cr));
  34. }
  35. int query(int l, int r, int node = 1, int cl = 1, int cr = n) {
  36. if(r < l)
  37. return inf;
  38. return _query(l, r);
  39. }
  40. }
  41. namespace LCA {
  42. int p[nbit][nmax];
  43. int pin[nmax], pout[nmax], inp = 1, preord[nmax], depth[nmax];
  44. void init(int node, int f) {
  45. p[0][node] = f;
  46. for(int i = 1; i < nbit; i++)
  47. p[i][node] = p[i - 1][p[i - 1][node]];
  48. pin[node] = inp;
  49. preord[inp++] = node;
  50. depth[node] = depth[f] + 1;
  51. for(auto x : g[node])
  52. if(x != f)
  53. init(x, node);
  54. pout[node] = inp - 1;
  55. return;
  56. }
  57. bool isanc(int f, int node) { return pin[f] <= pin[node] && pout[node] <= pout[f]; }
  58. int lca(int x, int y) {
  59. if(isanc(x, y))
  60. return x;
  61. if(isanc(y, x))
  62. return y;
  63. for(int i = nbit - 1; i >= 0; i--) {
  64. if(!isanc(p[i][x], y))
  65. x = p[i][x];
  66. }
  67. return p[0][x];
  68. }
  69. }
  70. #warning clist sa aiba santinela
  71. vector< vector<int> > clist;
  72. int atrcol[nmax];
  73. void insert( int x, int col) {
  74. clist[col].push_back(x);
  75. atrcol[x] = col;
  76. AINT::erase(LCA::pin[x]);
  77. }
  78. void descend(int node);
  79. void solve(int l, int r);
  80. int descend(int L, int R, int node, int col) {
  81. vector<pair<int,int> > candid;
  82. insert(node, col);
  83. for(auto x : g[node]) {
  84. if(atrcol[x] != 0)
  85. continue;
  86. if(x == LCA::p[0][node]) {
  87. candid.push_back({min(AINT::query(L, LCA::pin[node] - 1), AINT::query(LCA::pout[node] + 1, R)), x});
  88. continue;
  89. }
  90. candid.push_back({AINT::query(LCA::pin[x], LCA::pout[x]), x});
  91. }
  92. sort(candid.begin(), candid.end());
  93. if(candid.size() == 0)
  94. return node;
  95. return descend(L, R, candid[0].second, col);
  96. }
  97. void solve(int l, int r) {
  98. if(r < l)
  99. return;
  100. pair<int,int> rez;
  101. int x, y, lca;
  102. x = AINT::query(l, r);
  103. if(x == inf) {
  104. return;
  105. }
  106. int currcol = clist.size();
  107. clist.push_back(vector<int>());
  108. insert(x, currcol);
  109. y = AINT::query(l, r);
  110. if(y == inf)
  111. return;
  112. rez = {x, y};
  113. insert(y, currcol);
  114. lca = LCA::lca(x, y);
  115. atrcol[lca] = currcol;
  116. while(x != lca) insert(x, currcol), x = LCA::p[0][x];
  117. while(y != lca) insert(y, currcol), y = LCA::p[0][y];
  118. insert(lca, currcol);
  119. tie(x, y) = rez;
  120. auto elim = [&](int node) {
  121. for(auto candidate : g[node])
  122. if(LCA::p[0][node] != candidate && atrcol[candidate] == 0)
  123. solve(LCA::pin[candidate], LCA::pout[candidate]);
  124. };
  125. tie(x, y) = rez;
  126. x = descend(l, r, x, currcol);
  127. y = descend(l, r, y, currcol);
  128. lca = LCA::lca(x, y);
  129. while(LCA::depth[x] > LCA::depth[lca]) elim(x), x = LCA::p[0][x];
  130. while(LCA::depth[y] > LCA::depth[lca]) elim(y), y = LCA::p[0][y];
  131. elim(lca);
  132. solve(l, r);
  133. }
  134.  
  135. }
  136.  
  137. using namespace CentroidDecompLmfao;
  138. map<int, int> modcol;
  139. int res[nmax];
  140.  
  141. int main() {
  142. cin >> n;
  143. for(int i = 1, x, y; i < n; i++) {
  144. cin >> x >> y;
  145. g[x].push_back(y);
  146. g[y].push_back(x);
  147. }
  148. if(n == 1) {
  149. cout << "1\n";
  150. return 0;
  151. }
  152. clist.push_back(vector<int>());
  153. LCA::init(1, 1);
  154. AINT::construct(LCA::preord);
  155. solve(1, n);
  156. for(int i = 1, mn; i < clist.size(); i++) {
  157. mn = n;
  158. for(auto x : clist[i])
  159. mn = min(mn, x);
  160. modcol[mn] = i;
  161. }
  162. int count = 1;
  163. for(auto [mn, line] : modcol) {
  164. for(auto x : clist[line])
  165. res[x] = count;
  166. count++;
  167. }
  168. for(int i = 1; i <= n; i++)
  169. cout << res[i] << ' ';
  170. cout << '\n';
  171. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement