Codeforces 278C Learning Languages(并查集)

来源:互联网 发布:周立功单片机教程 编辑:程序博客网 时间:2024/06/05 06:04

题意抽象出来就是求联通块的个数吧,然后添加最少边使图联通。

注意所有人都不会任何语言的时候,答案是n而不是n-1。

#include<algorithm>#include<iostream>#include<cstring>#include<fstream>#include<sstream>#include<vector>#include<string>#include<cstdio>#include<bitset>#include<queue>#include<stack>#include<cmath>#include<map>#include<set>#define FF(i, a, b) for(int i=a; i<b; i++)#define FD(i, a, b) for(int i=a; i>=b; i--)#define REP(i, n) for(int i=0; i<n; i++)#define CLR(a, b) memset(a, b, sizeof(a))#define debug puts("**debug**")#define LL long long#define PB push_back#define MP make_pair#define eps 1e-8using namespace std;const int maxn = 111;int n, m, k, x, fa[maxn];set<int> lg[maxn];set<int> :: iterator it;int findset(int x) { return x == fa[x] ? x : fa[x] = findset(fa[x]); }bool check(int i, int j){    for(it=lg[i].begin(); it!=lg[i].end(); it++)        if(lg[j].find(*it) != lg[j].end()) return true;    return false;}int main(){    scanf("%d%d", &n, &m);    int cnt = 0;    FF(i, 1, n+1)    {        fa[i] = i;        scanf("%d", &k);        if(k == 0) cnt++;        while(k--)        {            scanf("%d", &x);            lg[i].insert(x);        }    }    if(cnt == n)    {        printf("%d\n", n);        return 0;    }    FF(i, 1, n+1) FF(j, i+1, n+1) if(check(i, j))    {        int x = findset(i), y = findset(j);        if(x != y) fa[x] = y;    }    int ans = 0;    FF(i, 1, n+1) if(fa[i] == i) ans++;    printf("%d\n", ans-1);    return 0;}


原创粉丝点击