使用带路径压缩的并查集,不然会TLE
AC代码:
#include <bits/stdc++.h> #define MP make_pair #define PB push_back #define st first #define nd second #define rd third #define rg register #define FOR(i, a, b) for(int i =(a); i <=(b); ++i) #define RE(i, n) FOR(i, 1, n) #define FORD(i, a, b) for(int i = (a); i >= (b); --i) #define REP(i, n) for(int i = 0;i <(n); ++i) #define VAR(v, i) __typeof(i) v=(i) #define FORE(i, c) for(VAR(i, (c).begin()); i != (c).end(); ++i) #define ALL(x) (x).begin(), (x).end() #define SZ(x) ((int)(x).size()) using namespace std; const int N = 100010; int id[N]; void init(int n) { for (int i = 1; i <= n; i++) id[i] = i; } int sear(int p) { while (id[p] != p) p = id[p]; return p; } int tran(int i) // 路径压缩 { int r = sear(i); while (i != r) { int p = id[i]; id[i] = r; i = p; } return r; } bool isun(int i, int j) { return sear(i) == sear(j); } void unio(int i, int j) { int p = tran(i), r = tran(j); if (p != r) id[p] = r; } int main() { int n, m, k, opera; cin >> n >> m; init(n); while(m--) { cin >> opera; switch(opera) { case 1: cin >> k >> n; unio(k, n); break; case 2: cin >> k >> n; if(isun(k, n)) cout << 'Y' << endl; else cout << 'N' << endl; break; } } return 0; }