Problem:
Score : 100 points

Problem Statement

You are given an undirected graph with N vertices and 0 edges. Process Q queries of the following types.

0 u v: Add an edge (u, v).

1 u v: Print 1 if u and v are in the same connected component, 0 otherwise.

Constraints

1 \leq N \leq 200,000

1 \leq Q \leq 200,000

0 \leq u_i, v_i \lt N

Input

Input is given from Standard Input in the following format:

N Q
t_1 u_1 v_1
t_2 u_2 v_2
:
t_Q u_Q v_Q

出力

For each query of the latter type, print the answer.

Sample Input 1

4 7
1 0 1
0 0 1
0 2 3
1 0 1
1 1 2
0 0 2
1 1 3

Sample Output 1

0
1
0
1

Solution in C++ (GCC 9.2.1) (judge verdict: Accepted)

#include <bits/stdc++.h>

#include <iostream>
//#include <algorithm>
// #include <iomanip>
#define ll long long
#define map unordered_map
#define set unordered_set
#define l_l pair<ll, ll>
#define vll vector<ll>
#define mll map<ll, ll>

using namespace std;

const ll MOD = 1000000007LL;
const ll INF = (1LL << 60LL);

struct UnionFind {
  vector<ll> data;

  UnionFind(ll sz) { data.assign(sz, -1); }

  bool unite(ll x, ll y) {
    x = find(x), y = find(y);
    if (x == y) return (false);
    if (data[x] > data[y]) swap(x, y);
    data[x] += data[y];
    data[y] = x;
    return (true);
  }

  ll find(ll k) {
    if (data[k] < 0) return (k);
    return (data[k] = find(data[k]));
  }

  ll size(ll k) { return (-data[find(k)]); }

  bool same(ll x, ll y) {
    int rx = find(x);
    int ry = find(y);
    return rx == ry;
  }
};

int main() {
  // std::cout << std::fixed << std::setprecision(10);

  auto uf = UnionFind(200010);

  ll N, Q;
  scanf("%lld %lld", &N, &Q);

  for (ll i = 0; i < Q; i++) {
    ll t, u, v;
    scanf("%lld %lld %lld", &t, &u, &v);

    if (t == 0) {
      uf.unite(u, v);
    }
    if (t == 1) {
      cout << (uf.same(u, v)) << endl;
    }
  }
}