108. 冗余连接
并查集应用类题目,关键是如何把题意转化成并查集问题
#include <iostream>
#include <vector>
using namespace std;
const int n = 1005;
vector<int>father(n);
void init() {
for (int i = 0; i < n; i++) {
father[i] = i;
}
}
int find(int u) {
return father[u] == u ? u : father[u] = find(father[u]);
}
bool isSame(int u, int v) {
u = find(u);
v = find(v);
return u == v;
}
void join(int u, int v) {
u = find(u);
v = find(v);
if (v == u)return;
father[u] = v;
}
void solve() {
int n;
cin >> n;
for (int i = 0; i < n; i++) {
int a, b;
cin >> a >> b;
if (isSame(a,b)) {
cout << a << " " << b << endl;
return;
}
join(a, b);
}
}
int main() {
init();
solve();
return 0;
}
109. 冗余连接II
上面两道题目是不是感觉做出自信了,感觉并查集不过如此?
来这道题目 给大家适当一些打击, 难度上来了。
#include <iostream>
#include <vector>
using namespace std;
int n;
vector<int>father(1005);
vector<vector<int>>nums;
void init() {
for (int i = 0; i < n; i++) {
father[i] = i;
}
}
int find(int u) {
return father[u] == u ? u : father[u] = find(father[u]);
}
bool isSame(int u, int v) {
u = find(u);
v = find(v);
return u == v;
}
void join(int u, int v) {
u = find(u);
v = find(v);
if (u == v)return;
father[u] = v;
}
bool isTreeAfterRemoveEdge(vector<vector<int>>nums, int deleteIndex) {
init();
for (int i = 0; i < n; i++) {
if (i == deleteIndex)continue;
if (isSame(nums[i][0], nums[i][1]))return false;
join(nums[i][0], nums[i][1]);
}
return true;
}
void getRemoveEdge(vector<vector<int>>nums) {
init();
for (int i = 0; i < n; i++) {
if (isSame(nums[i][0], nums[i][1])) {
cout << nums[i][0] << " " << nums[i][1] << endl;
return;
}
join(nums[i][0], nums[i][1]);
}
}
void solve() {
int a, b;
cin >> n;
vector<int>isDegree(n+1,0);//用来记录入度的次数
for (int i = 0; i < n; i++) {
cin >> a >> b;
nums.push_back({ a,b });
isDegree[b]++;
}
vector<int>vec;
for (int i = n - 1; i >= 0; i--) {
if (isDegree[nums[i][1]] == 2) {
vec.push_back(i);
}
}
if (!vec.empty()) {
if (isTreeAfterRemoveEdge(nums, vec[0])) {
cout << nums[vec[0]][0] << " " << nums[vec[0]][1] << endl;
}
else cout << nums[vec[1]][0] << " " << nums[vec[1]][1] << endl;
}
else getRemoveEdge(nums);
}
int main() {
init();
solve();
return 0;
}
总结
并查集用来写连成环的题。