HDU 4005 The war(边双连通+缩点)
来源:互联网 发布:网络销售彩票好做吗 编辑:程序博客网 时间:2024/04/29 02:40
题意:有一幅图,现在要加一条边,加边之后要你删除一条边,使图不连通,费用为边的费用,要你求的是删除的边的最小值的最大值(每次都可以删除一条边,选最小的删除,这些最小中的最大就为答案)。
思路:首先求出桥边然后缩点,这时候得到了一棵树,因为树上任意两点之间连一条线会形成一条环,所以我们就想使得环以外的最小边尽可能大。
首先考虑最小边,最小边一定在这个环上,然后以这条最小边的两个端点进行dfs,找出以这两个端点为根到子树的路径中的次小值,然后取两个次小值中的较小者就是答案。
#include<cstdio>#include<cstring>#include<cmath>#include<cstdlib>#include<iostream>#include<algorithm>#include<vector>#include<map>#include<queue>#include<stack>#include<string>#include<map>#include<set>#include<ctime>#define eps 1e-6#define LL long long#define pii pair<int, int>#pragma comment(linker, "/STACK:1024000000,1024000000")using namespace std;const int INF = 0x3f3f3f3f;const int MAXN = 10010;//点数const int MAXM = 200010;//边数int n, m;struct Edge{ int to, next, w;}edge[MAXM];int head[MAXN], tot;int Low[MAXN], DFN[MAXN], Stack[MAXN], Belong[MAXN];//Belong数组的值是1~Blockint Index, Top;int Block;//边双连通块数bool Instack[MAXN];vector<int> G[MAXN], W[MAXN]; //缩点后形成的图 bool tag;int node1, node2, minedge, ans;void addedge(int u,int v,int w){ edge[tot].to = v;edge[tot].next = head[u];edge[tot].w = w; head[u] = tot++;}void init(){memset(head,-1,sizeof(head));memset(DFN,0,sizeof(DFN)); memset(Instack,false,sizeof(Instack)); tag = Index = Top = Block = tot = 0; minedge = INF; ans = INF;for(int i = 1; i <= n; i++) G[i].clear(), W[i].clear();}void Tarjan(int u,int id){ int v; Low[u] = DFN[u] = ++Index; Stack[Top++] = u; Instack[u] = true; for(int i = head[u];i != -1;i = edge[i].next) { v = edge[i].to; if((i^1) == id) continue; if( !DFN[v] ) { Tarjan(v, i); if( Low[u] > Low[v] )Low[u] = Low[v]; } else if( Instack[v] && Low[u] > DFN[v]) Low[u] = DFN[v]; } if(Low[u] == DFN[u]) { Block++; do { v = Stack[--Top]; Instack[v] = false; Belong[v] = Block; } while( v!=u ); }}void suodian() {for(int i = 1; i <= n; i++) {for(int e = head[i]; e != -1; e = edge[e].next) {int u = edge[e].to, w = edge[e].w;if(Belong[u] != Belong[i]) {G[Belong[i]].push_back(Belong[u]);W[Belong[i]].push_back(w);if(w < minedge) {minedge = w;node1 = Belong[i], node2 = Belong[u];}tag = 1;}}}}int dfs(int cur, int fa) {int min1 = INF, min2 = INF;for(int i = 0; i < G[cur].size(); i++) {int u = G[cur][i];if(u == fa) continue;int tmp = dfs(u, cur);tmp = min(tmp, W[cur][i]);if(tmp < min1) min2 = min1, min1 = tmp;else if(tmp < min2) min2 = tmp;}ans = min(ans, min2);return min1;}int main() { //freopen("input.txt", "r", stdin);while(cin >> n >> m) {init();for(int i = 1, u, v, d; i <= m; i++) {scanf("%d%d%d", &u, &v, &d);addedge(u, v, d);addedge(v, u, d);}Tarjan(1, -1);suodian();if(!tag) {puts("-1");continue;}dfs(node1, node2);dfs(node2, node1);if(ans == INF) puts("-1");else cout << ans << endl; } return 0;}
0 0
- HDU 4005 The war(边双连通+缩点)
- 【HDU】4005 The war 边双连通
- HDU 4005 The war 边-双连通缩点+树形dp
- HDU - 4005 The war(dfs+边双连通)
- HDU 4005 The war(双连通好题)
- 【双连通分量】 HDOJ 4005 The war
- hdu 3749 点双连通
- hdu 3394(点双连通)
- hdu 5739(点双连通)
- HDU 5739(点双连通)
- hdu 4005(边双连通)
- HDU 4005 The war
- POJ 3352 Road Construction (边双连通,缩点)
- UVA 10972 RevolC FaeLoN(边-双连通+缩点)
- HDU -- 3844 Mining Your Own Business(点双连通)
- 【HDU 5739】Fantasia(点双连通+dfs)
- hdu 4005(双连通)
- hdu 4005 双连通
- IOS 开发 Swfit UIbutton高亮延迟处理方法
- sqlite数据库简单查询命令
- Android完美解析setContentView 你真的理解setContentView吗?
- 复合谓词定义
- 配置mysql日志输出
- HDU 4005 The war(边双连通+缩点)
- Android中的数据存储的五种方式
- SpringMVC介绍之视图解析器ViewResolver
- 关键字爬google的pdf
- ScollView中嵌套ListView问题
- 日期计算
- C#变量声明中var的使用
- LeetCode/Dynamic Programming/Unique Paths
- Android系列教程之Activity的生命周期