D - Cyclic Components 并查集好题

 

并查集

#include<iostream>  
#include<string.h>  
#include<algorithm>  
#include<cmath>  
#include<map>  
#include<string>  
#include<stdio.h>  
#include<vector>  
#include<stack>
#include<set>
using namespace std;
#define INIT ios::sync_with_stdio(false)
#define LL long long int
 
struct node {
    int id;
    int count;
};
int dp[2 * 100005];
vector<int>mm[200005];
void init() {
    for (int i = 0;i < 2 * 100005;i++) {
        dp[i] = i;
    }
}
 
int _find(int x) {
    if (dp[x] != x) {
        return dp[x] = _find(dp[x]);
    }
    return dp[x];
}
 
void _union(int  x, int y) {
    int xx = _find(x);
    int yy = _find(y);
    if (xx < yy) {
        dp[xx]= yy;
    }
    else {
        dp[yy] = xx;
    }
}
 
int main() {
    int n, m;
    map<int, int>mp;//存每个节点的度
    while (cin >> n >> m)
    {
        mp.clear();
        init();
        int a, b;
        int ans = 0;
        for (int i = 0;i < m;i++) {
            cin >> a >> b;
            mp[a]++;
            mp[b]++;
            if (_find(a) != _find(b)) {
                _union(a, b);
            }
        }
        //通过父节点把连通图存进一个vector数组
        for (int i = 1;i <= n;i++) {
            mm[_find(i)].push_back(i);
        }
        for (int i = 1;i <= n;i++) {
            //连通图至少要有3个点
            if (mm[i].size() > 2) {
                int flag = 1;
                for (int j = 0;j < mm[i].size()&&flag;j++) {
                    //只要有一个度不为2就跳出
                    if (mp[mm[i][j]] != 2) {
                        flag = 0;
                    }
                }
                if (flag)ans++;
            }
        }
        cout << ans << endl;
    }
    return 0;
}

 

posted @ 2020-03-14 23:12  SunCY  阅读(91)  评论(0编辑  收藏  举报