0
点赞
收藏
分享

微信扫一扫

【动态规划】树形dp:没有老板的舞会

码农K 2022-05-02 阅读 61

一颗数中挑选若干个节点使得值最大。

挑选规则:如果挑选了该节点,那么就不能选该节点的所有直接子节点。

 

 代码:

#include<iostream>
#include<vector>
using namespace std;
int v[10010],happy[10010];
int dp[10010][2];
int  n;
vector<int>son[10010];
//dp(x):表示求出dp[x][0]和dp[x][1] 
void DP(int x){
	dp[x][0]=0;
	dp[x][1]=happy[x];
	for(int i=0;i<son[x].size();i++){
		int y=son[x][i];
		//dp(y)表示求出dp[y][0]和dp[y][1] 
		DP(y);
		//当x节点不选时,取dp[y][0]和dp[y][1]的最大值 
		dp[x][0]+=max(dp[y][0],dp[y][1]);
		//当x节点选时,只能取dp[y][0] 
		dp[x][1]+=dp[y][0];
	}
}
int main(){
	cin>>n;
	for(int i=1;i<=n;i++)cin>>happy[i];
	for(int i=1;i<n;i++){
		int x,y;
		cin>>x>>y;
		v[x]=1;
		son[y].push_back(x);
	}
	int root=0;
	for(int i=1;i<=n;i++){
		if(!v[i]){
			root=i;
			break;
		}
	}
	DP(root);
	cout<<max(dp[root][0],dp[root][1]);
} 
举报

相关推荐

0 条评论