Advertisement
Dang_Quan_10_Tin

COUNTPROBS

Apr 8th, 2022
871
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 2.61 KB | None | 0 0
  1. #define task "COUNTPROBS"
  2. #include <iostream>
  3. #include <cstdio>
  4. #include <vector>
  5. #include <cassert>
  6.  
  7. using namespace std;
  8.  
  9. using ll = long long;
  10. using ld = long double;
  11.  
  12. template <class T>
  13. void read(T &x)
  14. {
  15.     x = 0;
  16.     register int c;
  17.  
  18.     while ((c = getchar()) && (c > '9' || c < '0'))
  19.         ;
  20.     for (; c >= '0' && c <= '9'; c = getchar())
  21.         x = x * 10 + c - '0';
  22. }
  23.  
  24. constexpr int N = 1e6 + 5;
  25. int n, m, l;
  26. vector<int> goodat[N], adj[N];
  27. vector<int> allvers[N * 3];
  28. int x[N * 2][21], ranks[N];
  29. int sumup[N], in[N];
  30.  
  31. void Read()
  32. {
  33.     // assert(cin >> n >> m);
  34.     read(n), read(m);
  35.  
  36.     for (int i = 1; i <= n; ++i)
  37.     {
  38.         int t;
  39.         // assert(cin >> t);
  40.         read(t);
  41.  
  42.         goodat[i].resize(t);
  43.  
  44.         for (auto &j : goodat[i])
  45.             // assert(cin >> j);
  46.             read(j);
  47.     }
  48.  
  49.     for (int i = 2; i <= n; ++i)
  50.     {
  51.         int p;
  52.         // assert(cin >> p);
  53.         read(p);
  54.  
  55.         adj[p].emplace_back(i);
  56.     }
  57. }
  58.  
  59. void dfs(int v)
  60. {
  61.     x[in[v] = ++l][0] = v;
  62.  
  63.     for (int i : adj[v])
  64.     {
  65.         ranks[i] = ranks[v] + 1;
  66.         dfs(i);
  67.         x[++l][0] = v;
  68.     }
  69. }
  70.  
  71. int LCA(int u, int v)
  72. {
  73.     int l = in[u], r = in[v];
  74.     if (l > r)
  75.         swap(l, r);
  76.  
  77.     int loga = __lg(r - l + 1);
  78.  
  79.     if (ranks[x[l][loga]] < ranks[x[r - (1 << loga) + 1][loga]])
  80.         return x[l][loga];
  81.  
  82.     return x[r - (1 << loga) + 1][loga];
  83. }
  84.  
  85. void Solve()
  86. {
  87.     ranks[1] = 1;
  88.     dfs(1);
  89.  
  90.     for (int i = l; i; --i)
  91.         if (i == in[x[i][0]])
  92.             for (auto j : goodat[x[i][0]])
  93.                 allvers[j].emplace_back(x[i][0]);
  94.  
  95.     // LCA O(1)
  96.     for (int i = 1; i < 21; ++i)
  97.         for (int j = 1; j <= l - (1 << i) + 1; ++j)
  98.             x[j][i] = (ranks[x[j][i - 1]] < ranks[x[j + (1 << (i - 1))][i - 1]] ? x[j][i - 1] : x[j + (1 << (i - 1))][i - 1]);
  99.  
  100.     for (int i = 1; i <= m; ++i)
  101.     {
  102.         for (int j = 0; j < (int)allvers[i].size(); ++j)
  103.         {
  104.             ++sumup[allvers[i][j]];
  105.  
  106.             if (j != (int)allvers[i].size() - 1)
  107.                 --sumup[LCA(allvers[i][j], allvers[i][j + 1])];
  108.         }
  109.     }
  110.  
  111.     for (int i = l; i; --i)
  112.         if (i == in[x[i][0]])
  113.             for (auto j : adj[x[i][0]])
  114.                 sumup[x[i][0]] += sumup[j];
  115.  
  116.     for (int i = 1; i <= n; ++i)
  117.         cout << sumup[i] << " ";
  118. }
  119.  
  120. int32_t main()
  121. {
  122.     ios_base::sync_with_stdio(0);
  123.     cin.tie(0);
  124.     cout.tie(0);
  125.  
  126.     if (fopen(task ".INP", "r"))
  127.     {
  128.         freopen(task ".INP", "r", stdin);
  129.         freopen(task ".OUT", "w", stdout);
  130.     }
  131.  
  132.     Read();
  133.     Solve();
  134. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement