Monday, May 20, 2019

[Gym] I - Sky Tax

Author            : Dipu Kumar Mohanto 
                    CSE, Batch - 6
                    BRUR.
Problem Statement : I - Sky Tax
Source            : Codeforces
Category          : Graph Theory
Algorithm         : LCA
Verdict           : Accepted

  1. #include <bits/stdc++.h>  
  2.   
  3. using namespace std;  
  4.   
  5. #define int                 long long int  
  6.   
  7. static const int maxn = 2e5 + 5;  
  8. static const int logn = 20;  
  9.   
  10.   
  11. vector <int> graph[maxn];  
  12. int depth[maxn], father[maxn][logn];  
  13. int subtreeSize[maxn];  
  14.   
  15. void dfs(int u, int p = -1)  
  16. {  
  17.       for (int i = 1; i < logn; i++) father[u][i] = father[ father[u][i-1] ][i-1];  
  18.       subtreeSize[u] = 1;  
  19.       for (int v : graph[u])  
  20.       {  
  21.             if (v == p) continue;  
  22.             depth[v] = depth[u] + 1;  
  23.             father[v][0] = u;  
  24.             dfs(v, u);  
  25.             subtreeSize[u] += subtreeSize[v];  
  26.       }  
  27. }  
  28.   
  29. int get_kth_parrent(int u, int k)  
  30. {  
  31.       for (int i = logn-1; i >= 0; i--)  
  32.       {  
  33.             if ((1 << i) <= k)  
  34.             {  
  35.                   u = father[u][i];  
  36.                   k -= (1 << i);  
  37.             }  
  38.       }  
  39.       return u;  
  40. }  
  41.   
  42. int lca(int u, int v)  
  43. {  
  44.       if (depth[u] < depth[v]) swap(u, v);  
  45.       for (int i = logn-1; i >= 0; i--)  
  46.       {  
  47.             if (depth[ father[u][i] ] >= depth[v])  
  48.             {  
  49.                   u = father[u][i];  
  50.             }  
  51.       }  
  52.       if (u == v) return u;  
  53.       for (int i = logn-1; i >= 0; i--)  
  54.       {  
  55.             if (father[u][i] != father[v][i])  
  56.             {  
  57.                   u = father[u][i];  
  58.                   v = father[v][i];  
  59.             }  
  60.       }  
  61.       return father[u][0];  
  62. }  
  63.   
  64.   
  65. signed main()  
  66. {  
  67.       ios_base::sync_with_stdio(false);  
  68.       cin.tie(nullptr);  
  69.       cout.tie(nullptr);  
  70.   
  71.       #ifndef ONLINE_JUDGE  
  72.             freopen("in.txt""r", stdin);  
  73.       #endif // ONLINE_JUDGE  
  74.   
  75.   
  76.       int tc;  
  77.       cin >> tc;  
  78.       for (int tcase = 1; tcase <= tc; tcase++)  
  79.       {  
  80.             int tnode, tquery, root;  
  81.             cin >> tnode >> tquery >> root;  
  82.             for (int e = 1; e < tnode; e++)  
  83.             {  
  84.                   int u, v;  
  85.                   cin >> u >> v;  
  86.                   graph[u].push_back(v);  
  87.                   graph[v].push_back(u);  
  88.             }  
  89.             depth[root] = 1;  
  90.             dfs(root);  
  91.             cout << "Case #" << tcase << ":\n";  
  92.             while (tquery--)  
  93.             {  
  94.                   int type;  
  95.                   cin >> type;  
  96.                   if (type == 0)  
  97.                   {  
  98.                         int nroot;  
  99.                         cin >> nroot;  
  100.                         root = nroot;  
  101.                   }  
  102.                   else  
  103.                   {  
  104.                         int x;  
  105.                         cin >> x;  
  106.                         int lcax = lca(root, x);  
  107.                         if (x == root)  
  108.                         {  
  109.                               cout << tnode << '\n';  
  110.                               continue;  
  111.                         }  
  112.                         if (lcax == root or (lcax != root && lcax != x))  
  113.                         {  
  114.                               cout << subtreeSize[x] << '\n';  
  115.                               continue;  
  116.                         }  
  117.                         assert(lcax == x);  
  118.                         int d = depth[root] + depth[x] - 2*depth[lcax];  
  119.                         int par = get_kth_parrent(root, d - 1);  
  120.                         int ans = tnode - subtreeSize[par];  
  121.                         cout << ans << '\n';  
  122.                   }  
  123.             }  
  124.             for (int i = 0; i < maxn; i++)  
  125.             {  
  126.                   graph[i].clear();  
  127.                   depth[i] = 0;  
  128.                   subtreeSize[i] = 0;  
  129.                   fill(begin(father[i]), end(father[i]), 0);  
  130.             }  
  131.       }  
  132.   
  133. }  

No comments:

Post a Comment

Note: Only a member of this blog may post a comment.