Problem p03855 (C++)

Buggy submission (status: Time Limit Exceeded):
#include <algorithm>
#include <cctype>
#include <deque>
#include <iomanip>
#include <iostream>
#include <map>
#include <queue>
#include <string>
#include <vector>

using namespace std;
#define REP(i, b, e) for (ll i = (ll)b; i < (ll)e; i++)
#define rep0(i, n) REP(i, 0ll, n)
#define rep1(i, n) REP(i, 1ll, n + 1)

#define shosu setprecision(13)

typedef long long ll;
typedef pair<ll, ll> P;
typedef pair<ll, P> Q;
// ll longinf=1ll<<60;
int inf = 1 << 29;
int dn[4] = {-1, 1, 0, 0};
int dm[4] = {0, 0, -1, 1};
ll longinf = (1ll << 60);

const ll MOD = 1e9 + 7;

class unionFind {
private:
  vector<int> parent;
  vector<int> rank;
  vector<int> sizes;

public:
  unionFind(int n) {
    rep0(i, n) {
      parent.push_back(i);
      rank.push_back(0);
      sizes.push_back(1);
    }
  }
  int root(int x) {
    if (parent[x] == x) {
      return x;
    } else {
      parent[x] = root(parent[x]);
      return parent[x];
    }
  }
  void merge(int x, int y) {
    x = root(x);
    y = root(y);
    if (x == y)
      return;
    if (rank[x] < rank[y])
      swap(x, y);
    if (rank[x] == rank[y])
      rank[x]++;
    parent[y] = x;
    sizes[x] += sizes[y];
  }
  bool same(int x, int y) { return root(x) == root(y); }
  int size(int x) { return sizes[root(x)]; }
};
int main() {
  int N, K, L;
  cin >> N >> K >> L;
  unionFind road(N);
  unionFind train(N);
  int p[K], q[K];
  rep0(i, K) {
    cin >> p[i] >> q[i];
    p[i]--, q[i]--;
    road.merge(p[i], q[i]);
  }
  int r[L], s[L];
  rep0(i, L) {
    cin >> r[i] >> s[i];
    r[i]--, s[i]--;
    train.merge(r[i], s[i]);
  }
  unionFind ans(N);
  rep0(i, N) {
    REP(j, i, N) {
      if (road.same(i, j) && train.same(i, j)) {
        ans.merge(i, j);
      }
    }
  }
  rep0(i, N) { cout << ans.size(i) << " "; }
  cout << endl;
}

Fixed submission:
#include <algorithm>
#include <cctype>
#include <deque>
#include <iomanip>
#include <iostream>
#include <map>
#include <queue>
#include <string>
#include <vector>

using namespace std;
#define REP(i, b, e) for (ll i = (ll)b; i < (ll)e; i++)
#define rep0(i, n) REP(i, 0ll, n)
#define rep1(i, n) REP(i, 1ll, n + 1)

#define shosu setprecision(13)

typedef long long ll;
typedef pair<ll, ll> P;
typedef pair<ll, P> Q;
// ll longinf=1ll<<60;
int inf = 1 << 29;
int dn[4] = {-1, 1, 0, 0};
int dm[4] = {0, 0, -1, 1};
ll longinf = (1ll << 60);

const ll MOD = 1e9 + 7;

class unionFind {
private:
  vector<int> parent;
  vector<int> rank;
  vector<int> sizes;

public:
  unionFind(int n) {
    rep0(i, n) {
      parent.push_back(i);
      rank.push_back(0);
      sizes.push_back(1);
    }
  }
  int root(int x) {
    if (parent[x] == x) {
      return x;
    } else {
      parent[x] = root(parent[x]);
      return parent[x];
    }
  }
  void merge(int x, int y) {
    x = root(x);
    y = root(y);
    if (x == y)
      return;
    if (rank[x] < rank[y])
      swap(x, y);
    if (rank[x] == rank[y])
      rank[x]++;
    parent[y] = x;
    sizes[x] += sizes[y];
  }
  bool same(int x, int y) { return root(x) == root(y); }
  int size(int x) { return sizes[root(x)]; }
};
int main() {
  int N, K, L;
  cin >> N >> K >> L;
  unionFind road(N);
  unionFind train(N);
  int p[K], q[K];
  rep0(i, K) {
    cin >> p[i] >> q[i];
    p[i]--, q[i]--;
    road.merge(p[i], q[i]);
  }
  int r[L], s[L];
  rep0(i, L) {
    cin >> r[i] >> s[i];
    r[i]--, s[i]--;
    train.merge(r[i], s[i]);
  }
  map<pair<int, int>, int> mp;
  rep0(i, N) { mp[{road.root(i), train.root(i)}]++; }
  rep0(i, N) { cout << mp[{road.root(i), train.root(i)}] << " "; }
  cout << endl;
}