其他分享
首页 > 其他分享> > P3174 [HAOI2009] 毛毛虫

P3174 [HAOI2009] 毛毛虫

作者:互联网

非常好的一道树形dp 我开始一直陷入了思维误区

认为最优解可能不但是从子树转移过来还可能是从父亲转移过来的

这就非常头疼了 转移方程不好写啊

但实际上直接从下向上转移就好 为什么

因为最优解 保证一定存在一个节点 最优解为该节点最大子树和次大子树之和 最为极端的情况就是 最优解那个节点只有一个子树 但是一定保证该节点是存在的

所以转移的时候 我们只要判断每个节点并且跟新ans就好

dp[u] 表示所有u的子树的最大值

max1表示最大值 max2表示次大值

还要特别判断 根节点和叶节点 这俩点比较特殊

更新ans的时候别忘记了还有fa也可以算进毛毛虫里面

点击查看代码
#include<bits/stdc++.h>
using namespace std;
#define lowbit(x) x&(-x)
#define ll long long
const int maxn=3e6+5;
int n,m,ans;
vector<int>Q[maxn];
int dp[maxn];
void dfs(int u,int fa);
int main(){
	cin>>n>>m;
	for(int i=1,aa,bb;i<=m;i++){
		cin>>aa>>bb;
		Q[aa].push_back(bb);
		Q[bb].push_back(aa);
	}
	dfs(1,-1);
	cout<<ans<<endl;
     return 0;
}
void dfs(int u,int fa){
	int max1=0,max2=0;
	for(int i=0;i<Q[u].size();i++){
		int to=Q[u][i];
		if(to==fa)continue;
		dfs(to,u);
		dp[u]=max(dp[to],dp[u]);
		if(dp[to]>=max1){
			max2=max1;
			max1=dp[to];
		}
		else if(dp[to]>=max2)
			max2=dp[to];
	}
	int cnt=Q[u].size()-1;
	if(fa==-1)cnt++;
	if(!cnt)
		dp[u]=1;
	else dp[u]+=cnt;
	if(cnt)
	ans=max(ans,max1+max2+cnt+1+(fa!=-1)-(max1!=0)-(max2!=0));
}

标签:cnt,int,max1,P3174,max2,HAOI2009,毛毛虫,节点,dp
来源: https://www.cnblogs.com/wzxbeliever/p/16081175.html