HDU 4912 LCA + 贪心

题意及思路

说一下为什么按LCA深度从深到浅贪心是对的。我们可以直观感受一下,一条的路径会影响以这个lca为根的这颗树中的链,而深度越深,影响范围越小,所以先选影响范围小的路径。

#include <bits/stdc++.h>
using namespace std;
const int maxn = 100010;
int head[maxn], Next[maxn * 2], ver[maxn * 2], tot, f[maxn][20];
int deep[maxn], t;
struct Edge {
	int u, v, lca, lca_deep;
	bool operator < (const Edge& rhs) const {
		return lca_deep > rhs.lca_deep;
	}
};
Edge a[maxn];
bool v[maxn];
void add(int x, int y) {
	ver[++tot] = y;
	Next[tot] = head[x];
	head[x] = tot;
}
queue<int> q;
void bfs() {
	deep[1] = 1;
	q.push(1);
	while(!q.empty()) {
		int x = q.front(); 
		q.pop();
		for (int i = head[x]; i; i = Next[i]) {
			int y = ver[i];
			if(deep[y]) continue;
			deep[y] = deep[x] + 1;
			f[y][0] = x;
			for (int j = 1; j <= t; j++)
				f[y][j] = f[f[y][j - 1]][j - 1];
			q.push(y);
		}
	}
}

int query(int x, int y) {
	if(deep[x] > deep[y]) swap(x, y);
	for (int i = t; i >= 0; i--) {
		if(deep[f[y][i]] >= deep[x]) y = f[y][i];
	}
	if(x == y) return x;
	for (int i = t; i >= 0; i--)
		if(f[x][i] != f[y][i]) {
			x = f[x][i], y = f[y][i];
		}
	return f[x][0];
}

void dfs(int x, int fa) {
	if(v[x]) return;
	v[x] = 1;
	for (int i = head[x]; i; i = Next[i]) {
		int y = ver[i];
		if(y == fa) continue;
		dfs(y, x);
	}
}

int main() {
	int n, m, x, y;
	while(~scanf("%d%d", &n, &m)) {
		t = (int)(log(n) / log(2)) + 1; 
		tot = 0;
		for (int i = 1; i <= n; i++) {
			head[i] = 0;
			v[i] = 0;
			for (int j = 0; j <= t; j++)
				f[i][j] = 0;
			deep[i] = 0;
		}
//		memset(head, 0, sizeof(head));
//		memset(f, 0, sizeof(f));
//		memset(v, 0, sizeof(v));
//		memset(deep, 0, sizeof(deep));
//		tot = 0;
		for (int i = 1; i < n; i++) {
			scanf("%d%d", &x, &y);
			add(x, y);
			add(y, x);
		}
		bfs();
		int ans = 0;
		for (int i = 1; i <= m; i++) {
			scanf("%d%d", &a[i].u, &a[i].v);
			a[i].lca = query(a[i].u, a[i].v);
			a[i].lca_deep = deep[a[i].lca];
		}
		sort(a + 1, a + 1 + m);
		for (int i = 1; i <= m; i++) {
			if(!v[a[i].u] && !v[a[i].v]) {
				ans++;
				dfs(a[i].lca, f[a[i].lca][0]);
			}
		}
		printf("%d\n", ans);
	}
}

  

posted @ 2019-04-02 10:56  维和战艇机  阅读(201)  评论(0编辑  收藏  举报