Warm up

题目连接:

http://acm.hdu.edu.cn/showproblem.php?pid=4612

Description

N planets are connected by M bidirectional channels that allow instant transportation. It's always possible to travel between any two planets through these channels.

  If we can isolate some planets from others by breaking only one channel , the channel is called a bridge of the transportation system.

People don't like to be isolated. So they ask what's the minimal number of bridges they can have if they decide to build a new channel.

  Note that there could be more than one channel between two planets.

  

Input

  The input contains multiple cases.

  Each case starts with two positive integers N and M , indicating the number of planets and the number of channels.

  (2<=N<=200000, 1<=M<=1000000)

  Next M lines each contains two positive integers A and B, indicating a channel between planet A and B in the system. Planets are numbered by 1..N.

  A line with two integers '0' terminates the input.

  

Output

For each case, output the minimal number of bridges after building a new channel in a line.

Sample Input

4 4

1 2

1 3

1 4

2 3

0 0

Sample Output

0

Hint

题意

让你加一条边,使得这个图的桥数量最小

输出桥的数量

题解:

先缩点,然后求一个直径,然后输出树边数减去直径就好了

这样显然最小

代码

#include <bits/stdc++.h>

using namespace std;
const int maxn = 200000 + 500;
struct edge{
int v , nxt;
}e[2005000];
int head[maxn] , tot , n , m , dfn[maxn] , low[maxn] , dfs_clock , bridge , dis[maxn] , vis[maxn] , Ftp , belong[maxn] ;
stack < int > sp;
vector < int > G[maxn];
void link(int u , int v){ e[tot].v=v,e[tot].nxt=head[u],head[u]=tot++;} void dfs(int x , int pre){
dfn[x] = low[x] = ++ dfs_clock; sp.push( x );
for(int i = head[x] ; ~i ; i = e[i].nxt ){
if( (i ^ 1) == pre ) continue;
int v = e[i].v;
if(!dfn[v]){
dfs( v , i );
low[x] = min( low[x] , low[ v ] );
if(low[v] > dfn[x]) bridge ++ ;
}else low[x]=min(low[x],dfn[v]);
}
if( low[x] == dfn[x] ){
++ Ftp;
while(1){
int u = sp.top() ; sp.pop();
belong[u] = Ftp;
if( u == x ) break;
}
}
} queue < int > Q; int solve(){
vis[1] = 1 ;
Q.push( 1 );
while(!Q.empty()){
int s = Q.front() ; Q.pop();
for(auto it : G[s]){
if( vis[it] == 0 ){
vis[it] = 1 ;
dis[it] = dis[s] + 1;
Q.push( it );
}
}
}
int s = -1 , index = 0;
for( int it = 1 ; it <= Ftp ; ++ it ){
if(dis[it] > s){
s = dis[it];
index = it;
}
}
for(int i = 1 ; i <= Ftp ; ++ i) dis[i] = vis[i] = 0;
Q.push( index );
vis[index] = 1;
while(!Q.empty()){
int s = Q.front() ; Q.pop();
for(auto it : G[s]){
if( vis[it] == 0 ){
vis[it] = 1 ;
dis[it] = dis[s] + 1;
Q.push( it );
}
}
}
s = 0;
for( int it = 1 ; it <= Ftp ; ++ it ){
if(dis[it] > s){
s = dis[it];
}
}
return s;
} int main(int argc,char *argv[]){
while(scanf("%d%d",&n,&m)){
if( n == 0 && m == 0 ) break;
for(int i = 1 ; i <= n ; ++ i) head[i] = -1 , dfn[i] = low[i] = vis[i] = dis[i] = 0 , G[i].clear();
tot = dfs_clock = bridge = Ftp = 0 ;
for(int i = 1 ; i <= m ; ++ i){
int u , v ;
scanf("%d%d",&u,&v);
link( u , v );
link( v , u );
}
for(int i = 1 ; i <= n ; ++ i) if(!dfn[i]) dfs( i , 1 << 30 );
for(int i = 1 ; i <= n ; ++ i)
for(int j = head[i] ; ~j ; j = e[j].nxt){
int v = e[j].v;
if(belong[i] == belong[v]) continue;
G[belong[i]].push_back( belong[v] );
G[belong[v]].push_back( belong[i] );
}
int maxv = solve();
printf("%d\n" , bridge - maxv );
}
return 0;
}

HDU 4612 Warm up tarjan 树的直径的更多相关文章

  1. Hdu 4612 Warm up (双连通分支+树的直径)

    题目链接: Hdu 4612 Warm up 题目描述: 给一个无向连通图,问加上一条边后,桥的数目最少会有几个? 解题思路: 题目描述很清楚,题目也很裸,就是一眼看穿怎么做的,先求出来双连通分量,然 ...

  2. F - Warm up - hdu 4612(缩点+求树的直径)

    题意:有一个无向连通图,现在问添加一条边后最少还有几个桥 分析:先把图缩点,然后重构图为一棵树,求出来树的直径即可,不过注意会有重边,构树的时候注意一下 *********************** ...

  3. HDU 4612 Warm up tarjan缩环+求最长链

    Warm up Problem Description   N planets are connected by M bidirectional channels that allow instant ...

  4. HDU 4612 Warm up(Tarjan)

    果断对Tarjan不熟啊,Tarjan后缩点,求树上的最长路,注意重边的处理,借鉴宝哥的做法,开标记数组,标记自己的反向边. #pragma comment(linker, "/STACK: ...

  5. HDU 4612——Warm up——————【边双连通分量、树的直径】

    Warm up Time Limit:5000MS     Memory Limit:65535KB     64bit IO Format:%I64d & %I64u Submit Stat ...

  6. 【HDU 4612 Warm up】BCC 树的直径

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=4612 题意:一个包含n个节点m条边的无向连通图(无自环,可能有重边).求添加一条边后最少剩余的桥的数 ...

  7. hdu 4612 Warm up 有重边缩点+树的直径

    题目链接 Warm up Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65535/65535 K (Java/Others)Tot ...

  8. 4612 warm up tarjan+bfs求树的直径(重边的强连通通分量)忘了写了,今天总结想起来了。

    问加一条边,最少可以剩下几个桥. 先双连通分量缩点,形成一颗树,然后求树的直径,就是减少的桥. 本题要处理重边的情况. 如果本来就两条重边,不能算是桥. 还会爆栈,只能C++交,手动加栈了 别人都是用 ...

  9. HDU 4612 Warm up(双连通分量缩点+求树的直径)

    思路:强连通分量缩点,建立一颗新的树,然后求树的最长直径,然后加上一条边能够去掉的桥数,就是直径的长度. 树的直径长度的求法:两次bfs可以求,第一次随便找一个点u,然后进行bfs搜到的最后一个点v, ...

随机推荐

  1. 残差网络(Residual Network)

    一.背景 1)梯度消失问题 我们发现很深的网络层,由于参数初始化一般更靠近0,这样在训练的过程中更新浅层网络的参数时,很容易随着网络的深入而导致梯度消失,浅层的参数无法更新. 可以看到,假设现在需要更 ...

  2. Workqueue机制的实现

    Workqueue机制中定义了两个重要的数据结构,分析如下: cpu_workqueue_struct结构.该结构将CPU和内核线程进行了绑定.在创建workqueue的过程中,Linux根据当前系统 ...

  3. 013 GC机制

    本文转自:https://www.cnblogs.com/shudonghe/p/3457990.html 最近还是在找工作,在面试某移动互联网公司之前认为自己对Java的GC机制已经相当了解,其他面 ...

  4. 设计模式之笔记--代理模式(Proxy)

    代理模式(Proxy) 定义 代理模式(Proxy),为其他对象提供一种代理以控制对这个对象的访问. 类图 描述 Subject,定义了ConcreteSubject和Proxy的共用接口,这样就可以 ...

  5. (总结)MySQL自带的性能压力测试工具mysqlslap详解

    PS:今天一同事问我有木有比较靠谱的mysql压力测试工具可用.其实mysql自带就有一个叫mysqlslap的压力测试工具,还是模拟的不错的.下面举例说说.mysqlslap是从5.1.4版开始的一 ...

  6. Linux 不常用命令总结

    1. vim编辑模式下,搜索,/user,跳转下一个,小写的n 2.

  7. mysql 配置数据库主从同步

    参考:https://www.cnblogs.com/kevingrace/p/6256603.html http://www.51testing.com/html/00/130600-243651. ...

  8. JAVA封装消息中间件调用一(kafka生产者篇)

    这段时间因为工作关系一直在忙于消息中间件的发开,现在趁着项目收尾阶段分享下对kafka的一些使用心得. kafka的原理我这里就不做介绍了,可参考http://orchome.com/kafka/in ...

  9. java1.8环境配置+win10系统

    Java环境配置相关 Java jdk 1.8版本的环境配置和1.7版本 存在一些差异,当然不同的操作系统可能会对jdk配置有一定的变化.本文我主要说1.8版本的jdk在window10 系统上的配置 ...

  10. javascript练习(二)

    案例 输出100个数字 案例  打印100以内 7的倍数 案例  打印100以内的奇数 案例  打印100以内所有偶数的和 打印图形 ********** ********** ********** ...