使用带路径压缩的并查集,不然会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;
}