1319. 连通网络的操作次数
知识点:并查集
时间:2021年1月23日
题目链接
题目
用以太网线缆将 n 台计算机连接成一个网络,计算机的编号从 0 到 n-1。线缆用 connections 表示,其中 connections[i] = [a, b] 连接了计算机 a 和 b。
网络中的任何一台计算机都可以通过网络直接或者间接访问同一个网络中其他任意一台计算机。
给你这个计算机网络的初始布线 connections,你可以拔开任意两台直连计算机之间的线缆,并用它连接一对未直连的计算机。请你计算并返回使所有计算机都连通所需的最少操作次数。如果不可能,则返回 -1 。
示例 1:
输入:n = 4, connections = [[0,1],[0,2],[1,2]]
输出:1
解释:拔下计算机 1 和 2 之间的线缆,并将它插到计算机 1 和 3 上。
示例 2:
输入:n = 6, connections = [[0,1],[0,2],[0,3],[1,2],[1,3]]
输出:2
示例 3:
输入:n = 6, connections = [[0,1],[0,2],[0,3],[1,2]]
输出:-1
解释:线缆数量不足。
示例 4:
输入:n = 5, connections = [[0,1],[0,2],[3,4],[2,3]]
输出:0
提示:
- 1 <= n <= 10^5
- 1 <= connections.length <= min(n*(n-1)/2, 10^5)
- connections[i].length == 2
- 0 <= connections[i][0], connections[i][1] < n
- connections[i][0] != connections[i][1]
- 没有重复的连接。
- 两台计算机不会通过多条线缆连接。
解题思路
- 并查集模版题 读题就可
- 如果节点个数-1 > 线的个数 肯定连接不了
- 否则把所有的线连起来后 看有几个连通分量
- 需要的线就是连通分量个数-1
代码
#include "cheader.h"
class Solution {
public:
struct UN{
vector<int> ancestor;
UN(int x){
ancestor.resize(x);
for(int i = 0; i < x;i++)
ancestor[i] = i;
}
int find(int x){
if(ancestor[x] == x)
return x;
else
return ancestor[x] = find(ancestor[x]);
}
void merge(int x,int y){
ancestor[find(x)] = ancestor[find(y)];
}
};
int makeConnected(int n, vector<vector<int>>& connections) {
UN un = UN(n);
int m = connections.size();
if(n-1 > m)
return -1;
for(int i = 0; i < m; i++){
int x = connections[i][0];
int y = connections[i][1];
if(un.find(x) != un.find(y))
un.merge(x, y);
}
int ans = 0;
for(int i = 0; i < n; i++){
if(un.find(i) == i)
ans++;
}
return --ans;
}
};
int main()
{
int n = 6;
vector<vector<int>> connections;
connections.push_back({0,1});connections.push_back({0,2});connections.push_back({0,3});
connections.push_back({1,2});connections.push_back({1,3});
Solution s;
cout<<s.makeConnected(n, connections)<<endl;
return 0;
}
今天也是爱zz的一天哦!