POJ-3352-RoadConstruction(边双联通分量,缩点)
生活随笔
收集整理的這篇文章主要介紹了
POJ-3352-RoadConstruction(边双联通分量,缩点)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
鏈接:https://vjudge.net/problem/POJ-3352#author=0
題意:
給一個無向連通圖,至少添加幾條邊使得去掉圖中任意一條邊不改變圖的連通性(即使得它變為邊雙連通圖)。
思路:
將圖中的邊雙聯通分量全部縮成一個點,得到度為1的點的數目。
若要使縮點后的圖都邊雙聯通,增加(leaf+1)/2條邊即可。leaf就是度為1的點。
代碼:
#include <iostream> #include <memory.h> #include <string> #include <istream> #include <sstream> #include <vector> #include <stack> #include <algorithm> #include <map> #include <queue> #include <math.h> #include <cstdio> #include <set> #include <iterator> #include <cstring> using namespace std;typedef long long LL; const int MAXN = 1e3+10;vector<int> G[MAXN]; stack<int> St; int Dfn[MAXN], Low[MAXN]; int Dis[MAXN], Fa[MAXN]; int times, res, cnt; int n, m;void Init() {for (int i = 1;i <= n;i++)G[i].clear();memset(Dfn, 0, sizeof(Dfn));memset(Low, 0, sizeof(Low));memset(Dis, 0, sizeof(Dis));memset(Fa, 0, sizeof(Fa));times = res = cnt = 0; }void Tarjan(int u, int v) {Dfn[v] = Low[v] = ++times;St.push(v);for (int i = 0;i < G[v].size();i++){int node = G[v][i];if (node == u)continue;if (Dfn[node] == 0)Tarjan(v, node);Low[v] = min(Low[v], Low[node]);}if (Dfn[v] == Low[v]){cnt++;int node;do{node = St.top();Fa[node] = cnt;St.pop();}while (node != v);} }int main() {string s;int t;while (cin >> n >> m){int l, r; // cin >> n >> m;Init();for (int i = 1;i <= m;i++){cin >> l >> r;G[l].push_back(r);G[r].push_back(l);}Tarjan(0, 1); // copy(Fa+1, Fa+1+n, ostream_iterator<int> (cout, " ")); // copy(Dis+1, Dis+1+n, ostream_iterator<int> (cout, " ")); // cout << endl;for (int i = 1;i <= n;i++){for (int j = 0;j < G[i].size();j++){int node = G[i][j];if (node == i)continue;if (Fa[i] != Fa[node])Dis[Fa[node]]++;}}int leaf = 0;for (int i = 1;i <= cnt;i++){if (Dis[i] == 1)leaf++;} // cout << "Output for Sample Input " << t << endl;cout << (leaf+1)/2 << endl;}return 0; }
轉載于:https://www.cnblogs.com/YDDDD/p/10857168.html
總結
以上是生活随笔為你收集整理的POJ-3352-RoadConstruction(边双联通分量,缩点)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: AJPFX关于构造器的总结
- 下一篇: 如何成为阿里巴巴大数据开发工程师?你要学