Leikouチェックイン2021.1.23によってネットワークに接続するための操作の数

トピック:
イーサネットケーブルを使用してn台のコンピューターをネットワークに接続します。コンピューター番号は0からn-1です。ケーブルは接続で表されます。ここで、connections [i] = [a、b]はコンピューターaとbを接続します。

ネットワーク内の任意のコンピューターは、ネットワークを介して同じネットワーク内の他のコンピューターに直接または間接的にアクセスできます。

このコンピュータネットワークの最初の配線接続を提供するために、直接接続されている2台のコンピュータ間のケーブルを抜き、それを使用して、直接接続されていないコンピュータのペアを接続できます。すべてのコンピューターを接続するために必要な最小操作数を計算して返します。それが不可能な場合は、-1が返されます。
ここに画像の説明を挿入
入力:n = 4、接続= [[0,1]、[0,2]、[1,2]]
出力:1
説明:コンピューター1と2の間のケーブルを抜き、コンピューター1と3に差し込みます。オン。
ここに画像の説明を挿入
入力:n = 6、接続= [[0,1]、[0,2]、[0,3]、[1,2]、[1,3]]
出力:2
例3:

入力:n = 6、接続= [[0,1]、[0,2]、[0,3]、[1,2]]
出力:-1
説明:ケーブルの数が不足しています。
例4:

入力:n = 5、接続= [[0,1]、[0,2]、[3,4]、[2,3]]
出力:0

コード

// 并查集模板
class UnionFind {
    
    
public:
    vector<int> parent;
    vector<int> size;
    int n;
    // 当前连通分量数目
    int setCount;
    
public:
    UnionFind(int _n): n(_n), setCount(_n), parent(_n), size(_n, 1) {
    
    
        iota(parent.begin(), parent.end(), 0);
    }
    
    int findset(int x) {
    
    
        return parent[x] == x ? x : parent[x] = findset(parent[x]);
    }
    
    bool unite(int x, int y) {
    
    
        x = findset(x);
        y = findset(y);
        if (x == y) {
    
    
            return false;
        }
        if (size[x] < size[y]) {
    
    
            swap(x, y);
        }
        parent[y] = x;
        size[x] += size[y];
        --setCount;
        return true;
    }
    
    bool connected(int x, int y) {
    
    
        x = findset(x);
        y = findset(y);
        return x == y;
    }
};

class Solution {
    
    
public:
    int makeConnected(int n, vector<vector<int>>& connections) {
    
    
        if (connections.size() < n - 1) {
    
    
            return -1;
        }

        UnionFind uf(n);
        for (const auto& conn: connections) {
    
    
            uf.unite(conn[0], conn[1]);
        }

        return uf.setCount - 1;
    }
};

おすすめ

転載: blog.csdn.net/weixin_45780132/article/details/113034982