[BZOJ]1123 [POI2008]BLO 割点

本文介绍了一道名为BLO的POI2008算法竞赛题目,该题目涉及图论中的割点概念。文章详细讲解了如何使用Tarjan算法求解每个节点作为割点时的影响,并提供了完整的C++代码实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1123: [POI2008]BLO

Time Limit: 10 Sec   Memory Limit: 162 MB
Submit: 1301   Solved: 591
[ Submit][ Status][ Discuss]

Description

Byteotia城市有n个 towns m条双向roads. 每条 road 连接 两个不同的 towns ,没有重复的road. 所有towns连通。

Input

输入n<=100000 m<=500000及m条边

Output

输出n个数,代表如果把第i个点去掉,将有多少对点不能互通。

Sample Input

5 5
1 2
2 3
1 3
3 4
4 5

Sample Output

8
8
16
14
8

HINT

Source

[ Submit][ Status][ Discuss]


HOME Back

    割点板子题.

    在tarjan的时候记录一下size即可. 注意乘2.

#include<stdio.h>
#include<algorithm>
using namespace std;
typedef long long dnt;
const int maxn = 100005;
dnt ans[maxn];
int n, m, num, indexx;
int low[maxn], dfn[maxn], siz[maxn], h[maxn];
struct edge{ int nxt, v;}e[1000005];
inline void add(int u, int v){
	e[++num].v = v, e[num].nxt = h[u], h[u] = num;
	e[++num].v = u, e[num].nxt = h[v], h[v] = num;
}
inline void dfs(int u){
	siz[u] = 1;
	dfn[u] = low[u] = ++indexx;
	int sum = 0;
	for(int i = h[u]; i; i = e[i].nxt){
		int v = e[i].v;
		if(dfn[v]) low[u] = min(low[u], dfn[v]);
		else{
			dfs(e[i].v);
			siz[u] += siz[v];
			low[u] = min(low[u], low[v]);
			if(low[v] >= dfn[u]){
				ans[u] += (dnt) sum * siz[v];
				sum += siz[v];
			}
		}
	}
	ans[u] += (dnt) sum * (n - sum - 1);
}
int main(){
	scanf("%d%d", &n, &m);
	for(int i = 1; i <= m; ++i){
		int u, v;
		scanf("%d%d", &u, &v);
		add(u, v);
	}
	dfs(1);
	for(int i = 1; i <= n; ++i) printf("%lld\n", (ans[i] + n - 1) * 2);
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值