首页 > 其他分享 >POI2011DYN-Dynamite

POI2011DYN-Dynamite

时间:2024-04-20 16:55:57浏览次数:22  
标签:tmp cnt cur int POI2011DYN second Dynamite first

POI #Year2011 #二分 #树上dp

二分答案

对于每个点 \(dp_{x,0/1}\) 表示到 \(x\) ,\(dp_{x,0}\)表示最远的没有被覆盖的点的距离 ,\(dp_{x,1}\) 表示最近的被选中的点的距离

转移按照题意,如果可以覆盖就覆盖,否则当留下来不合法就加点

// Author: xiaruize
const int N = 3e5 + 10;

int head[N], to[N<<1], nxt[N<<1], tot;

void add(int u, int v)
{
	tot++;
	to[tot] = v;
	nxt[tot] = head[u];
	head[u] = tot;
}

int n, m;
bool st[N];
vector<int> g[N];
int cnt = 0;

pii dfs(int x, int fa, int lim)
{
	pii cur = {-INF, INF};
	for (int i = head[x]; i; i = nxt[i])
	{
		int v = to[i];
		if (v == fa)
			continue;
		auto tmp = dfs(v, x, lim);
		cur.first = max(cur.first, tmp.first + 1);
		cur.second = min(cur.second, tmp.second + 1);
	}
	if (cur.first + cur.second <= lim)
		cur.first = -INF;
	if (cur.second > lim && st[x])
		cur.first = max(cur.first, 0);
	if (cur.first == lim)
	{
		cur = {-INF, 0};
		cnt++;
	}
	return cur;
}

bool check(int x)
{
	cnt = 0;
	pii tmp = dfs(1, 0, x);
	if (tmp.first >= 0)
		cnt++;
	return cnt <= m;
}

void solve()
{
	cin >> n >> m;
	rep(i, 1, n) cin >> st[i];
	rep(i, 1, n - 1)
	{
		int u, v;
		cin >> u >> v;
		add(u, v);
		add(v, u);
	}
	int l = 0, r = n;
	while (l < r)
	{
		int mid = l + r >> 1;
		if (check(mid))
			r = mid;
		else
			l = mid + 1;
	}
	cout << r << endl;
}

#ifndef ONLINE_JUDGE
bool end_of_memory_use;
#endif

signed main()
{
	// freopen(".in","r",stdin);
	// freopen(".out","w",stdout);
	ios::sync_with_stdio(false);
	cin.tie(0);
	cout.tie(0);
	int testcase = 1;
	// cin >> testcase;
	while (testcase--)
		solve();
#ifndef ONLINE_JUDGE
	cerr << "Memory use:" << (&end_of_memory_use - &start_of_memory_use) / 1024.0 / 1024.0 << "MiB" << endl;
	cerr << "Time use:" << (double)clock() / CLOCKS_PER_SEC * 1000.0 << "ms" << endl;
#endif
	return 0;
}

标签:tmp,cnt,cur,int,POI2011DYN,second,Dynamite,first
From: https://www.cnblogs.com/xiaruize/p/18147869

相关文章

  • P3523 [POI2011] DYN-Dynamite
    P3523[POI2011]DYN-Dynamite二分+树上贪心首先这题可以二分\(K\),转化为判定性问题:是否存在\(m\)个点使得所有关键节点的\(dis\leK\)。那么意思就是,每个点可以控制\(K\)距离以内的关键点。那么我们可以从叶子节点向上贪心,实在覆盖不到了再选点。那么我们要判断该点是......
  • 【动态规划】【贪心】 [POI2011] DYN-Dynamite
    这俩东西是怎么结合到一起的?题目描述给一棵树,树上有一些关键节点,要求你选\(m\)个点,第\(i\)个关键节点到这些点中每个点距离的最小值记为\(dis_i\),记这全部\(dis\)的最大值为\(K\),现在要使\(K\)最小,求这个\(K\)。\(1\leqn,m\leq3\times10^5\)。算法描述让最......
  • 解题报告—Dynamite
    Dynamite给一棵树,树上有一些关键节点,要求你选\(m\)个点,第\(i\)个关键节点到这些点中每个点距离的最小值记为\(dis_i\),记这全部\(dis\)的最大值为\(K\),现在要使\(......
  • DLR 的扩展库 Dynamitey
    .NET在CLR对动态语言或者脚本语言的支持是通过DLR完成的,MigueldeIcaza对DLR的特点概括如下:一个针对动态语言的共享式类型系统;一个共享的AST,可以被语言开发人员......