hdu1520 Anniversary party 简单树形DP

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1520

思路:树形DP的入门题

定义dp[root][1]表示以root为根节点的子树,且root本身参加party的最优值,那么dp[root][1]+=Σdp[son][0]+happy[root];

dp[root][0]表示以root为跟节点且root本身没有参加的最优值,那么dp[root][0]+=max(dp[son][0],dp[son][1]);

如果不理解,可以参考我对hdu1054的解释。

代码如下:

 1 #include<iostream>
 2 #include<cstdlib>
 3 #include<cstdio>
 4 #include<cstring>
 5 using namespace std;
 6 #define MAX 6010
 7 int dp[MAX][2];
 8 int happy[MAX];
 9 class node
10 {
11   public:
12   int to;
13   int next;
14 };
15 node edge[2*MAX];
16 int head[MAX];
17 int vis[MAX];
18 int n;
19 int tol;
20 void init()
21 {
22   memset(vis,0,sizeof(vis));
23   memset(head,-1,sizeof(head));
24   memset(dp,0,sizeof(dp));
25   tol=0;
26 }
27 void Build_Tree(int u,int v)
28 {
29         edge[tol].to=v;
30         edge[tol].next=head[u];
31         head[u]=tol++;
32 }
33 void dfs(int root)
34 {
35    vis[root]=1;
36    int hy=happy[root];
37    for(int i=head[root];i!=-1;i=edge[i].next)
38    {
39      if(vis[edge[i].to]) continue;
40      int son=edge[i].to;
41      dfs(son);
42 
43      dp[root][1]+=dp[son][0];
44      dp[root][0]+=max(dp[son][1],dp[son][0]);
45    }
46    dp[root][1]+=hy;
47 }
48 int main()
49 {
50    while(scanf("%d",&n)!=EOF)
51    {
52      init();
53      for(int i=1;i<=n;i++)
54        scanf("%d",&happy[i]);
55        int u,v;
56 
57        while(scanf("%d%d",&v,&u)!=EOF&&v&&u)
58        {
59         Build_Tree(u,v);
60         Build_Tree(v,u);
61        }
62     dfs(1);
63     cout<<max(dp[1][1],dp[1][0])<<endl;
64    }
65   return 0;
66  }
View Code

 

 

posted on 2013-08-18 16:58  GyyZyp  阅读(137)  评论(0编辑  收藏  举报

导航