POJ 3694——Network——————【连通图,LCA求桥】
Time Limit:5000MS Memory Limit:65536KB 64bit IO Format:%I64d & %I64u
Description
A network administrator manages a large network. The network consists of N computers and M links between pairs of computers. Any pair of computers are connected directly or indirectly by successive links, so data can be transformed between any two computers. The administrator finds that some links are vital to the network, because failure of any one of them can cause that data can't be transformed between some computers. He call such a link a bridge. He is planning to add some new links one by one to eliminate all bridges.
You are to help the administrator by reporting the number of bridges in the network after each new link is added.
Input
The input consists of multiple test cases. Each test case starts with a line containing two integers N(1 ≤ N ≤ 100,000) and M(N - 1 ≤ M ≤ 200,000).
Each of the following M lines contains two integers A and B ( 1≤ A ≠ B ≤ N), which indicates a link between computer A and B. Computers are numbered from 1 to N. It is guaranteed that any two computers are connected in the initial network.
The next line contains a single integer Q ( 1 ≤ Q ≤ 1,000), which is the number of new links the administrator plans to add to the network one by one.
The i-th line of the following Q lines contains two integer A and B (1 ≤ A ≠ B ≤ N), which is the i-th added new link connecting computer A andB.
The last test case is followed by a line containing two zeros.
Output
For each test case, print a line containing the test case number( beginning with 1) and Q lines, the i-th of which contains a integer indicating the number of bridges in the network after the first i new links are added. Print a blank line after the output for each test case.
Sample Input
3 2
1 2
2 3
2
1 2
1 3
4 4
1 2
2 1
2 3
1 4
2
1 2
3 4
0 0
Sample Output
Case 1:
1
0 Case 2:
2
0
题目大意:n个点,m条边。q次询问,问你新加入无向边ui,vi后,图中的桥还有多少。
解题思路:求桥,标记桥,LCA过程中消去桥。
#include<stdio.h>
#include<algorithm>
#include<string.h>
#include<vector>
using namespace std;
const int maxn = 100100;
struct Edge{
int from,to,dist,next;
Edge(){}
Edge(int _to,int _next):to(_to),next(_next){}
}edges[maxn*4];
int dfn[maxn];
int fa[maxn],bridge[maxn],dep[maxn];
int head[maxn];
int tot, brinum;
int dfs_clock;
void init(){
tot = 0;
dfs_clock = 0;
brinum = 0;
memset(head,-1,sizeof(head));
memset(bridge,0,sizeof(bridge));
memset(dfn,0,sizeof(dfn));
}
void AddEdge(int _u,int _v){
edges[tot].to = _v;
edges[tot].next = head[_u];
head[_u] = tot++;
}
int dfs(int u,int f){
int lowu = dfn[u] = ++dfs_clock;
int child = 0;
for(int i = head[u]; i != -1; i = edges[i].next){
int v = edges[i].to;
if(!dfn[v]){
child++;
fa[v] = u;
int lowv = dfs(v,i);
lowu = min(lowv,lowu);
if(lowv > dfn[u]){ //标记桥
bridge[v] = 1;
brinum++;
}
}else if(dfn[v] < dfn[u] && (f^1) != i){
lowu = min(lowu,dfn[v]);
}
}
// low[u] = lowu;
return lowu;
}
void LCA(int u,int v){ //简化的LCA,把求LCA过程中的桥减掉
while(dfn[u] < dfn[v]){
if(bridge[v] == 1){
brinum--;
bridge[v] = 0;
}
v = fa[v];
}
while(dfn[u] > dfn[v]){
if(bridge[u] == 1){
brinum--;
bridge[u] = 0;
}
u = fa[u];
}
while( u != v ){
if(bridge[u]) {
brinum--;
bridge[u] = 0;
}
if(bridge[v]){
brinum--;
bridge[v] = 0;
}
u = fa[u];
v = fa[v];
}
}
int main(){
int n, m, q, cas = 0;
while(scanf("%d%d",&n,&m)!=EOF&&(n+m)){
int a,b;
init();
for(int i = 0; i < m; i++){
scanf("%d%d",&a,&b);
AddEdge(a,b);
AddEdge(b,a);
}
for(int i = 1; i <= n; i++){
if(!dfn[i])
dfs(i,-1);
}
printf("Case %d:\n",++cas);
scanf("%d",&q);
for(int i = 0; i < q; i++){
scanf("%d%d",&a,&b);
LCA(a,b);
printf("%d\n",brinum);
}puts("");
}
return 0;
}
POJ 3694——Network——————【连通图,LCA求桥】的更多相关文章
- Poj 3694 Network (连通图缩点+LCA+并查集)
题目链接: Poj 3694 Network 题目描述: 给出一个无向连通图,加入一系列边指定的后,问还剩下多少个桥? 解题思路: 先求出图的双连通分支,然后缩点重新建图,加入一个指定的边后,求出这条 ...
- poj 3694 Network(割边+lca)
题目链接:http://poj.org/problem?id=3694 题意:一个无向图中本来有若干条桥,有Q个操作,每次加一条边(u,v),每次操作后输出桥的数目. 分析:通常的做法是:先求出该无向 ...
- Network POJ - 3694 (连通图标求桥)
有上述两个数组定义可知:对于某点root,其有一儿子v,则有: 1. 如果dfn[root]<=low[v]此点是割点(对于dfs树的根,即最初节点需要两个儿子才是割点) 2. ...
- POJ 3694 Network (tarjan + LCA)
题目链接:http://poj.org/problem?id=3694 题意是给你一个无向图n个点,m条边,将m条边连接起来之后形成一个图,有Q个询问,问将u和v连接起来后图中还有多少个桥. 首先用t ...
- kuangbin专题 专题九 连通图 POJ 3694 Network
题目链接:https://vjudge.net/problem/POJ-3694 题目:给定一个连通图,求桥的个数,每次查询,加入一条边,问加入这条边后还有多少个桥. 思路:tarjan + 并查集 ...
- poj 3417 Network(tarjan lca)
poj 3417 Network(tarjan lca) 先给出一棵无根树,然后下面再给出m条边,把这m条边连上,然后每次你能毁掉两条边,规定一条是树边,一条是新边,问有多少种方案能使树断裂. 我们设 ...
- POJ 3694 Network (求桥,边双连通分支缩点,lca)
Network Time Limit: 5000MS Memory Limit: 65536K Total Submissions: 5619 Accepted: 1939 Descripti ...
- POJ 3694 Network(并查集缩点 + 朴素的LCA + 无向图求桥)题解
题意:给你一个无向图,有q次操作,每次连接两个点,问你每次操作后有几个桥 思路:我们先用tarjan求出所有的桥,同时我们可以用并查集缩点,fa表示缩点后的编号,还要记录每个节点父节点pre.我们知道 ...
- POJ 3694 Network(无向图求桥+重边处理+LCA)
题目大意: 给你一个无向图,然后再给你一个Q代表有Q次询问,每一次加一条边之后还有几座桥.在这里要对重边进行处理. 每次加入一条边之后,在这条搜索树上两个点的公共祖先都上所有点的桥都没了. 这里重边的 ...
随机推荐
- VS2015无法创建C++工程解决方法!!
VS2015默认安装时候没有安装C++,如果安装C++没有选择全部C++项目,则无法创建C++工程,在控制面板里的删除程序中,选择VS2015,随后选择修改,把C++项目都选择上就可以了,这样安装完毕 ...
- c语言——数组指针和通过指针引用数组元素的方法总结
1.数组指针:即指向数组的指针 那么, 如何声明一个数组指针呢?int (* p)[10]; /*括号是必须写的,不然就是指针数组:10是数组的大小*/1拓展:有指针类型元素的数组称为指针数组. 2. ...
- findControl 可以获取前台页面的控件
findControl 可以获取前台页面的控件
- Python学习过程(五)
这里记录下python怎么去和数据库打交道,也就是这么怎么去连接数据库,以及对数据库的操作,我这里用的sqlserver, 好了,首先当然是引入我们的模块包: import pymssql 猜的不错的 ...
- Java实现微信小程序支付(支付,提现,退款)
1.添加WXpayCommon类用以具体实现功能,代码如下: package com.karat.cn.wxCommon; import java.io.IOException; import jav ...
- crm web ui
1:View中的field对应于model中的attribute. 2:custom controller具有更长的生存时间,能够在view中共享一些数据. 3:window是component的一个 ...
- 使用windows服务修改CPU型号(重启依然有效)
此项目基于.net framework 4.0 效果如下: 服务运行前: 服务运行后: 思路大概是这样: 通过修改注册表可以修改CPU型号,把服务设置成本地服务,并且开机自动启动,来实现开机自动修改处 ...
- 关于string 的简单应用
声明||作用 string类本不是STL的容器,但是它与STL容器有着很多相似的操作,因此,把string放在这里一起进行介绍. 之所以抛弃char*的字符串而选用C++标准程序库中的string类, ...
- 基本数据类型 list and tuple 04
列表和元组 一,列表 1.列表 由[]括起来 可以存放各种数据类型: 存放量比较大 2.列表的索引和切片 列表也有索引 lst [i] i 即列表中各元素的位置 2.1列表的切片 lst[star ...
- 压测工具 ab jmeter
apach ab|abs ab -n -c xxx.html/js/css jmeter siege 用途:测试分布式锁是否有效, 测试java Lock是否使用正确,测试接口吞吐量