Problem p03045 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <cmath>
#include <deque>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <stack>
#include <string>
#include <vector>
using namespace std;
typedef long long ll;
typedef vector<int> VI;
#define FOR(i, n) for (int(i) = 0; (i) < (n); (i)++)
#define FOR1(i, n) for (int(i) = 1; (i) < (n); (i)++)
#define eFOR(i, n) for (int(i) = 0; (i) <= (n); (i)++)
#define eFOR1(i, n) for (int(i) = 1; (i) <= (n); (i)++)
#define SORT(i) sort((i).begin(), (i).end())
#define rSORT(i) sort((i).begin(), (i).end(), greater<int>());
#define YES(i) cout << ((i) ? "Yes" : "No") << endl;
constexpr auto INF = 1000000000;
constexpr auto LLINF = 922337203685477580; // 7;
constexpr auto mod = 1000000007;

class unionfind {
  VI par, rank;

public:
  void init(int N) {
    par.clear();
    rank.clear();
    for (int i = 0; i < N; i++)
      par.push_back(i);
    for (int i = 0; i < N; i++)
      rank.push_back(1);
  }
  int root(int x) {
    if (par[x] == x)
      return x;
    return par[x] = root(par[x]);
  }
  int size(int x) {
    if (par[x] == x)
      return rank[x];
    return size(par[x]);
  }
  void unite(int x, int y) {
    int rx = root(x);
    int ry = root(y);
    if (rx == ry)
      return;
    if (rank[rx] < rank[ry]) {
      par[rx] = ry;
      rank[ry] += rank[rx];
    } else {
      par[ry] = rx;
      rank[rx] += rank[ry];
    }
  }
  bool same(int x, int y) { return root(x) == root(y); }
};

int main() {

  int n, m;
  cin >> n >> m;
  VI x(n), y(n), z(n);
  FOR(i, m) {
    cin >> x[i] >> y[i] >> z[i];
    x[i]--;
    y[i]--;
  }

  unionfind UF;
  UF.init(n);
  FOR(i, m) UF.unite(x[i], y[i]);
  set<int> ans;
  FOR(i, n) ans.insert(UF.root(i));
  cout << ans.size() << endl;
}

Fixed submission:
#include <algorithm>
#include <cmath>
#include <deque>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <stack>
#include <string>
#include <vector>
using namespace std;
typedef long long ll;
typedef vector<int> VI;
#define FOR(i, n) for (int(i) = 0; (i) < (n); (i)++)
#define FOR1(i, n) for (int(i) = 1; (i) < (n); (i)++)
#define eFOR(i, n) for (int(i) = 0; (i) <= (n); (i)++)
#define eFOR1(i, n) for (int(i) = 1; (i) <= (n); (i)++)
#define SORT(i) sort((i).begin(), (i).end())
#define rSORT(i) sort((i).begin(), (i).end(), greater<int>());
#define YES(i) cout << ((i) ? "Yes" : "No") << endl;
constexpr auto INF = 1000000000;
constexpr auto LLINF = 922337203685477580; // 7;
constexpr auto mod = 1000000007;

class unionfind {
  VI par, rank;

public:
  void init(int N) {
    par.clear();
    rank.clear();
    for (int i = 0; i < N; i++)
      par.push_back(i);
    for (int i = 0; i < N; i++)
      rank.push_back(1);
  }
  int root(int x) {
    if (par[x] == x)
      return x;
    return par[x] = root(par[x]);
  }
  int size(int x) {
    if (par[x] == x)
      return rank[x];
    return size(par[x]);
  }
  void unite(int x, int y) {
    int rx = root(x);
    int ry = root(y);
    if (rx == ry)
      return;
    if (rank[rx] < rank[ry]) {
      par[rx] = ry;
      rank[ry] += rank[rx];
    } else {
      par[ry] = rx;
      rank[rx] += rank[ry];
    }
  }
  bool same(int x, int y) { return root(x) == root(y); }
};

int main() {

  int n, m;
  cin >> n >> m;
  VI x(m), y(m), z(m);
  FOR(i, m) {
    cin >> x[i] >> y[i] >> z[i];
    x[i]--;
    y[i]--;
  }

  unionfind UF;
  UF.init(n);
  FOR(i, m) UF.unite(x[i], y[i]);
  set<int> ans;
  FOR(i, n) ans.insert(UF.root(i));
  cout << ans.size() << endl;
}