Codeforces 278C Learning Languages(並查集)

題意抽象出來就是求聯通塊的個數吧,然後添加最少邊使圖聯通。

注意所有人都不會任何語言的時候,答案是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-8
using 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;
}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章