Advertisement
erek1e

POI Task Monkeys

Jul 9th, 2023
820
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 1.90 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <algorithm>
  4.  
  5. using namespace std;
  6.  
  7. // DSU
  8. vector<int> parent;
  9. vector<vector<int>> component;
  10. int root(int i) {
  11.     return parent[i] < 0 ? i : (parent[i] = root(parent[i]));
  12. }
  13. void unite(int i, int j) {
  14.     i = root(i), j = root(j);
  15.     if (i == j) return;
  16.     if (parent[i] > parent[j]) swap(i, j);
  17.     parent[i] += parent[j];
  18.     component[i].insert(component[i].end(), component[j].begin(), component[j].end());
  19.     parent[j] = i;
  20.     component[j].clear();
  21. }
  22.  
  23. int main() {
  24.     ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
  25.     int n, m; cin >> n >> m;
  26.     vector<vector<int>> holding(1+n, vector<int>(2, -1));
  27.     for (int i = 1; i <= n; ++i) cin >> holding[i][0] >> holding[i][1];
  28.     vector<pair<int, int>> changes(m);
  29.     for (int i = 0; i < m; ++i) {
  30.         int monkey, hand; cin >> monkey >> hand;
  31.         --hand;
  32.         int &fellow = holding[monkey][hand];
  33.         changes[i] = {monkey, fellow};
  34.         fellow = -1;
  35.     }
  36.  
  37.     // dsu with component members with additional log(n)
  38.     parent.assign(1+n, -1);
  39.     component.resize(1+n);
  40.     for (int i = 1; i <= n; ++i) component[i] = {i};
  41.     for (int i = 1; i <= n; ++i) {
  42.         for (int j = 0; j < 2; ++j) {
  43.             if (holding[i][j] != -1) unite(i, holding[i][j]);
  44.         }
  45.     }
  46.  
  47.     vector<int> groundTime(1+n);
  48.     int r = root(1);
  49.     for (int x : component[r]) groundTime[x] = -1;
  50.  
  51.     for (int i = (int)changes.size()-1; i >= 0; --i) {
  52.         auto [monkey, fellow] = changes[i];
  53.         r = root(1);
  54.         int r1 = root(monkey), r2 = root(fellow);
  55.         if (r1 == r2) continue;
  56.         if (r2 == r) swap(monkey, fellow), swap(r1, r2);
  57.         if (r1 == r) {
  58.             for (int x : component[r2]) groundTime[x] = i;
  59.         }
  60.         unite(monkey, fellow);
  61.     }
  62.     for (int i = 1; i <= n; ++i) cout << groundTime[i] << '\n';
  63.     return 0;
  64. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement