【agc004d】Teleporter

题目大意

一棵树,改变一些边的父亲,使得深度不超过k。

解题思路

我一开始就想到了贪心,结果莫名其妙的把这种方法给否决了,
然后考虑优化树形dp,然后优化失败⊙﹏⊙
贪心思路很简单,也很好感受出来,从下往上跑,每当到底下的深度大于k,将其断掉,连向根节点。

#include <cmath>
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <queue>
#include <map>
#include <bitset>
#include <set>
const int maxlongint=2147483647;
const int mo=1e9+7;	
const int N=100005;
using namespace std;
int n,m,ans,deep[N],a[N];
int tot,nt[N*2],lt[N*2],to[N*2];
bool bz[N];
void link(int x,int y)
{
	nt[++tot]=lt[x];
	lt[x]=tot;
	to[tot]=y;
}
int dg(int x,int fa)
{
	deep[x]=deep[fa]+1;
	int mx=deep[x];
	for(int i=lt[x];i;i=nt[i]) mx=max(dg(to[i],x),mx);
	if(x==1) return 0;
	if(fa!=1 && mx-deep[x]+1==m) ans++,mx=0;
	return mx;
}
int main()
{
	scanf("%d%d",&n,&m);
	for(int i=1;i<=n;i++)
	{
		scanf("%d",&a[i]);
		if(i!=1) link(a[i],i);
	}
	if(a[1]!=1) ans++;
	deep[0]=-1;
	dg(1,0);
	printf("%d",ans);
}
原文地址:https://www.cnblogs.com/chen1352/p/9099508.html