1579. 保证图可完全遍历 并查集

Alice 和 Bob 共有一个无向图,其中包含 n 个节点和 3  种类型的边:

类型 1:只能由 Alice 遍历。
类型 2:只能由 Bob 遍历。
类型 3:Alice 和 Bob 都可以遍历。
给你一个数组 edges ,其中 edges[i] = [typei, ui, vi] 表示节点 ui 和 vi 之间存在类型为 typei 的双向边。请你在保证图仍能够被 Alice和 Bob 完全遍历的前提下,找出可以删除的最大边数。如果从任何节点开始,Alice 和 Bob 都可以到达所有其他节点,则认为图是可以完全遍历的。

返回可以删除的最大边数,如果 Alice 和 Bob 无法完全遍历图,则返回 -1 。

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/remove-max-number-of-edges-to-keep-graph-fully-traversable
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

注意实例化两个并查集实例,来进行操作。

class UnionFind {
public:
    unordered_map <int, int> fa;
    unordered_map <int, int> rank;
    int setCount;
    
    UnionFind(int n): setCount(n) {}

    int find(int x) {
        if (!fa.count(x)) {
            fa[x] = x;
            rank[x] = 1;
        }
        return fa[x] == x ? fa[x] : fa[x] = find(fa[x]);
    }

    bool same(int x, int y) {
        return find(x) == find(y);
    }

    bool merge(int x, int y) {
        int xx = find(x);
        int yy = find(y);
        if (same(xx, yy)) {
            return false;
        }
        if (rank[xx] < rank[yy]) {
            swap(xx, yy);
        }
        rank[xx] += rank[yy];
        fa[yy] = xx;
        setCount--;
        return true;
    }
};

class Solution {
public:
    int maxNumEdgesToRemove(int n, vector<vector<int>>& edges) {
        int ans = 0;
        UnionFind ufA(n), ufB(n);

        for (auto& edge : edges) {
            edge[1]--;
            edge[2]--;
        }

        for (auto edge : edges) {
            if (edge[0] == 3) {
                int u = edge[1];
                int v = edge[2];
                if (!ufA.merge(u, v)) {
                    ans++;
                }
                else {
                    ufB.merge(u, v);
                }
            }
        }

        for (auto edge : edges) {
            int u = edge[1];
            int v = edge[2];
            if (edge[0] == 1) {
                if (!ufA.merge(u, v)) {
                    ans++;
                }
            }
            else
            if (edge[0] == 2) {
                if (!ufB.merge(u, v)) {
                    ans++;
                }
            }
        }

        if (ufA.setCount != 1 || ufB.setCount != 1) {
            return -1;
        }
        return ans;
    }
};
posted @ 2021-01-27 23:30  _西瓜不甜  阅读(80)  评论(0编辑  收藏  举报