POJ3177 Redundant Paths【边双联通分量】【Tarjan】

题目链接:

?id=3177

题目大意:

Bessie的农场有F块牧场,已知当前任意两个农场之间至少有一条路径相连(并不一定直接相连)

为了从某块牧场移动到另一块牧场,,Bessie和她的伙伴经常需要经过腐烂的树林。奶牛们特别

反感经过不好走的路,于是Bessie决定在农场种再建几条路,使得在去某个地方时总能够有两

条完全独立的路可够选择。那么问题来了:F块牧场,R条路,问至少再修几条路就能使得农场

中任意两个牧场之间都有至少两条相互独立的路径。

思路:

为了使农场中任意两个牧场之间都有至少两条相互独立的路径。也就是把F块牧场看做点,R条

路看做是两个农场之间的双向边。那么问题就转换为:最少添加几条边,可以使图不存在割边。

也就是和POJ3352一样的问题:最少添加几条边,使得任意两个边连通分量之间相互双连通。

具体做法参考博文:

注:此题比POJ3352多了一点,需要判重。。。所以我用了Map[][]数组。

AC代码:

#include<iostream>#include<algorithm>#include<cstdio>#include<cstring>using namespace std;const int MAXN = 5050;const int MAXM = 50500;bool Map[MAXN][MAXN];struct EdgeNode{int to;int next;}Edges[MAXM];int Head[MAXN];int dfn[MAXN],low[MAXN],Stack[MAXN],degree[MAXN];int m,id,scc,lay,M,N;void AddEdges(int u,int v){Edges[id].to = v;Edges[id].next = Head[u];Head[u] = id++;}void TarjanBFS(int pos,int from){//Stack[m++] = pos;dfn[pos] = low[pos] = ++lay;for(int i = Head[pos]; i != -1; i = Edges[i].next){if(Edges[i].to == from)continue;if( !dfn[Edges[i].to] ){TarjanBFS(Edges[i].to,pos);low[pos] = min(low[pos],low[Edges[i].to]);//if( dfn[pos] < low[Edges[i].to] )//{//while(Stack[m–] != Edges[i].to);//}}elselow[pos] = min(low[pos],low[Edges[i].to]);}}int main(){int u,v;while(~scanf("%d%d",&N,&M)){memset(Head,-1,sizeof(Head));memset(dfn,0,sizeof(dfn));memset(low,0,sizeof(low));memset(degree,0,sizeof(degree));m = lay = scc = id = 0;memset(Map,0,sizeof(Map));for(int i = 0; i < M; ++i){scanf("%d%d",&u,&v);if(Map[u][v] == 0){AddEdges(u,v);AddEdges(v,u);Map[u][v] = Map[v][u] = 1;}}TarjanBFS(1,-1);for(int i = 1; i <= N; ++i){for(int j = Head[i]; j != -1; j = Edges[j].next){if(low[i] != low[Edges[j].to])degree[low[i]]++;}}int ans = 0;for(int i = 1; i <= N; ++i)if(degree[i] == 1)ans++;printf("%d\n",(ans+1)/2);}return 0;}

只想到处流浪人生就像一场旅行,不必在乎目的地,

POJ3177 Redundant Paths【边双联通分量】【Tarjan】

相关文章:

你感兴趣的文章:

标签云: