並查集,向量偏移再來一發。
這個題就比上次那個食物鏈的要簡單了。
跟龍幫虎幫的那個是一樣的。
題目意思好變態:告訴兩個蟲子是異性,告訴你跟多的節點的信息,問你有沒有同性戀的一對蟲子。
/*
兩種情況的向量偏移的題目。
*/
#include<iostream>
#include<stdio.h>
using namespace std;
const int N = 2010;
int father[N];
int rank[N];
void InitSet(int n)
{
for(int i = 1 ; i <= n ; i++)
{
father[i] = i;
rank[i] = 0;
}
}
int FindSet(int n)
{
if(n != father[n])
{
int t = father[n];
father[n] = FindSet(father[n]);
rank[n] = (rank[t] + rank[n])%2;/*路徑壓縮,更新rank[i],沿着父節點到祖先節點的路徑*/
}
return father[n];
}
void UnionSet(int a,int b,int d)
{
int x = FindSet(a);
int y = FindSet(b);
father[x] = y;
rank[x] = (rank[a] - rank[b] + 2 + d)%2;/*合併向量化簡更新rank[]數組*/
}
int main()
{
int ncase;
scanf("%d",&ncase);
int cnt = 0;
while(ncase--)
{
cnt++;
int n,m;
scanf("%d %d",&n,&m);
InitSet(n);
bool flag = false;
for(int i = 0 ; i < m ; i++)
{
int a,b;
scanf("%d %d",&a,&b);
int x = FindSet(a);
int y = FindSet(b);
if(x == y)
{
if(rank[a] == rank[b])
{
flag = true;
}//不能跳出,會造成終止文件輸入!!
}
else
{
UnionSet(a,b,1);
}
}
printf("Scenario #%d:\n",cnt);
if(flag)
{
printf("Suspicious bugs found!\n");
}
else
{
printf("No suspicious bugs found!\n");
}
printf("\n");
}
return 0;
}