题意:bug有两种性别,每个bug是两个性别之一,现在给出两个bug的关系,bug之间只允许异性恋,求出所有bug中是否存在同性恋
思路:种类并查集。每个节点赋予权值,根的权值为两节点权值的同或和,判断根相同的两节点权值是否相同即可
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<vector>
#include<stack>
#include<queue>
#include<map>
#include<algorithm>
using namespace std;
typedef long long ll;
const int maxn = 1e6+10;
const int inf = 0x3f3f3f3f;
int n, u[maxn], d[maxn], m, T;
int ufind(int x)
{
if (u[x] < 0) return x;
int t = ufind(u[x]);
d[x] ^= d[u[x]];
u[x] = t;
return t;
}
bool unite(int x, int y)
{
int a = ufind(x), b = ufind(y);
if (a == b) {
if (d[x] == d[y])
return 1;
else
return 0;
}
u[b] = a;
d[b] = !(d[x]^d[y]);
return 0;
}
int main()
{
scanf("%d", &T);
for (int t = 1; t <= T; t++) {
scanf("%d%d", &n, &m);
memset(d, 0, sizeof(d));
memset(u, -1, sizeof(u));
int x, y, flag = 0;
for (int i = 0; i < m; i++) {
scanf("%d%d", &x, &y);
if (unite(x, y)) {
flag = 1;
}
}
if (!flag)
printf("Scenario #%d:\nNo suspicious bugs found!\n\n", t);
else
printf("Scenario #%d:\nSuspicious bugs found!\n\n", t);
}
return 0;
}