ASC1 C New Year Bonus Grant

题意:给你一棵树,有三种规则

1)根节点不能选

2)选了这个点 它 的父亲节点和子节点都不能选。

3)一个点只能选其中的一个子节点。

问你选点的最大值

解题思路:树形DP。DP[I][1/0]表示选或不选最大的。

解题代码:

 1 // File Name: c.cpp
 2 // Author: darkdream
 3 // Created Time: 2015年03月21日 星期六 14时55分57秒
 4 
 5 #include<vector>
 6 #include<list>
 7 #include<map>
 8 #include<set>
 9 #include<deque>
10 #include<stack>
11 #include<bitset>
12 #include<algorithm>
13 #include<functional>
14 #include<numeric>
15 #include<utility>
16 #include<sstream>
17 #include<iostream>
18 #include<iomanip>
19 #include<cstdio>
20 #include<cmath>
21 #include<cstdlib>
22 #include<cstring>
23 #include<ctime>
24 #define LL long long
25 
26 using namespace std;
27 int dp[500005][2];
28 vector<int> mp[500005];
29 int hs[500005];
30 int mxfrom[500005];
31 void dfs(int k)
32 {
33     if(mp[k].size() == 0 )
34     {
35         dp[k][1] = 1;
36         dp[k][0] = 0 ;
37         return ; 
38     }
39     dp[k][1] = 1;
40     for(int i = 0 ;i < mp[k].size();i ++)
41     {
42         dfs(mp[k][i]);
43         dp[k][0] += dp[mp[k][i]][0];
44         dp[k][1] += dp[mp[k][i]][0];
45     }
46     int tt = dp[k][0];
47     for(int i = 0 ;i < mp[k].size();i ++)
48     {
49         if(tt < dp[k][0] - dp[mp[k][i]][0] + dp[mp[k][i]][1])
50         {
51             mxfrom[k] = mp[k][i];
52             tt = dp[k][0] - dp[mp[k][i]][0] + dp[mp[k][i]][1];
53         }
54     }
55     dp[k][0] = tt; 
56 }
57 int tt; 
58 int a[500005];
59 void findans(int k,int v)
60 {
61     if(v == 1)
62     {
63         tt ++ ; 
64         a[tt] = k ; 
65     }
66     for(int i = 0 ;i < mp[k].size(); i ++) 
67     {
68         if(mp[k][i] == mxfrom[k])
69             findans(mp[k][i],1);
70         else 
71             findans(mp[k][i],0);
72     }
73 }
74 int main(){
75     freopen("grant.in","r",stdin);
76     freopen("grant.out","w",stdout);
77     int n; 
78     scanf("%d",&n);
79     int tmp ;
80     for(int i= 2;i <= n;i ++)
81     {
82         scanf("%d",&tmp);
83         mp[tmp].push_back(i);
84     }
85     dfs(1);
86     printf("%d
",dp[1][0]*1000);
87     findans(1,0);
88     sort(a+1,a+1+tt);
89     for(int i = 1;i <= tt;i ++)
90     {
91         printf(i == 1?"%d":" %d",a[i]) ;    
92     }
93     printf("
");
94     return 0;
95 }
View Code
没有梦想,何谈远方
原文地址:https://www.cnblogs.com/zyue/p/4356431.html