带边权的并查集
#include<bits/stdc++.h>
using namespace std;
const int N = 1e6+10;
int f[N], num[N], d[N];
///d[i]表示i到祖宗的距离,num[i]表示以i为祖宗的队列的长度,是否清零都可以,因为合并后就用不到了
int Find(int x)
{
if(x == f[x]) return x;
int root = Find(f[x]);
d[x] += d[f[x]]; ///更新祖先,并同时更新x到祖先的距离
f[x] = root;
return root;
}
void merge(int x, int y) ///把x所处的队列放在y所处的队列后面
{
x = Find(x), y = Find(y);
if(x == y) return ;
f[x] = y; ///更改x的祖先为y
d[x] += num[y]; ///更新x到祖先的距离,就是原距离加上以y为祖先的队列的长度
num[y] += num[x]; ///把x的数量加到y为祖先的队列中
num[x] = 0;
}
int main()
{
int T;
cin>>T;
for(int i = 1; i <= N; ++i) f[i] = i, num[i] = 1;
while(T--)
{
string op;
int x, y;
cin>>op>>x>>y;
if(op[0] == 'M') merge(x, y);
else{
int tx = Find(x), ty = Find(y);
if(tx != ty) puts("-1");
else printf("%d\n", max(abs(d[x]-d[y])-1, 0));
}
}
return 0;
}