InputThe first line contains a number T(T≤30)T(T≤30)——The number of the testcases.
For each testcase, the first line contains a number n(n≤100)n(n≤100).
Then n+1 lines follow. Each line contains two numbers u,vu,v , which means there is an edge between u and v.OutputFor each testcase, print a single number.Sample Input
1 3 1 2 2 3 3 1 1 3
Sample Output
9
題意:給出n個點,和n+1條邊,問可以有多少種去掉邊的方法,使去掉邊后整個圖仍然是連通的
題解:使用並查集來判斷是否連通,再通過逐個枚舉去掉一條邊和去掉兩條邊的情況,判斷整個圖是否連通,如果是則ans++ 否則ans不變
#include<iostream> #include<cstdio> using namespace std; int s[105], e[105]; int t, n; int a, b; int pre[105]; int Find(int r) { return pre[r] = pre[r] == r ? r : Find(pre[r]); } int check(int a, int b) { for (int i = 1; i <= n; i++) { pre[i] = i; } for (int i = 0; i <= n; i++) { //與a , b 相連的邊直接去掉,查看是否還能夠全部聯通 if (i == a || i == b) continue; int f1 = Find(s[i]), f2 = Find(e[i]); if (f1 != f2) pre[f1] = f2; } int cnt = 0; for (int i = 1; i <= n; i++) { if (pre[i] == i) cnt++; if (cnt > 1) return 0; } return 1; } int main() { cin >> t; while (t--) { cin >> n; for (int i = 0; i <= n; i++) { cin >> s[i] >> e[i]; } int ans = 0; //逐個查找,i = j 代表是取一條邊,不等代表是取兩條邊 //要想全部聯通至少需要n-1條邊 for (int i = 0; i <= n; i++) { for (int j = i; j <= n; j++) { ans += check(i, j); } } cout << ans << endl; } return 0; }
本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。