2019ICPC沈阳网络赛 B. Dudu's maze

题目链接:https://www.jisuanke.com/contest/3007?view=challenges

解题思路:
首先我们需要把所有不是monster的点使用并查集缩点,然后枚举每一个monster去找到他们所得到的贡献值最大的那个,最后输出。(求贡献的时候可以直接用并查集求,我刚开始用dfs回溯来求,一直超时)

注意点:
1.注意monster不能被作为子节点求贡献

代码:

#include <iostream>
#include <cstdio>
#include <cstring>

using namespace std;

const int N = 1e5 + 50, M = 4e5 + 100;

int T, n, m, k;
int h[N], out[N], e[M], ne[M], idx;
int f[N], cnt[N];
bool monster[N];

inline void add(int a, int b) {
	e[idx] = b, ne[idx] = h[a], h[a] = idx ++;
	e[idx] = a, ne[idx] = h[b], h[b] = idx ++;
	out[a] ++, out[b] ++;
} 

inline int find(int x) { return x == f[x] ? f[x] : f[x] = find(f[x]); }

int main(void) {
//	freopen("in.txt", "r", stdin);
	scanf("%d", &T);
	while(T --) {
		scanf("%d%d%d", &n, &m, &k);
		memset(h, -1, sizeof h);
		for(int i = 1; i <= m; i ++) {
			int a, b; scanf("%d%d", &a, &b);
			add(a, b); 
		} 
		for(int i = 1; i <= k; i ++) {
			int tmp; scanf("%d", &tmp);
			monster[tmp] = true;
		}
		for(int i = 1; i <= n; i ++) f[i] = i, cnt[i] = 1;

		for(int i = 1; i <= n; i ++) {
			if(monster[i]) continue;
			for(int j = h[i]; j + 1 ;j = ne[j]) {
				int v = e[j]; 
				if(monster[v]) continue;
				int x = find(i), y = find(v);
				if(x != y) {
					f[x] = y;
					cnt[y] += cnt[x];
				}
			}
		}

		double ans = 0;
		int permt = find(1);
		for(int i = 1; i <= n; i ++) {
			int tmp1 = 0; 
			double tmp2 = 0;
			if(monster[i]) {
				for(int j = h[i]; j + 1; j = ne[j]) {
					int v = e[j];
					if(monster[v]) continue;
					int vv = find(v);
					if(vv == permt) tmp1 ++;
					else tmp2 += cnt[vv];
				}
				
				if(tmp1 > 0)
					ans = max(ans, tmp2 / out[i]);
			}
		}

		ans += cnt[permt];
		printf("%lf\n", ans);
		
		memset(out, 0, sizeof out); idx = 0;
		memset(monster, false, sizeof monster);
	}
	
//	fclose(stdin);
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值