HackerRank Even Tree(树dp)

Posted AC_Arthur

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HackerRank Even Tree(树dp)相关的知识,希望对你有一定的参考价值。

题目链接:点击打开链接

思路:

简单证明了一下,贪心不可行,  那么我们考虑树形dp。   用d[u]表示以u为根的子树的最优解。 u的儿子v,如果以v为根的子树数目为偶数, 那么可以考虑选择断掉u和v的边(决策1), 也可以不断, 递归下去(决策2)。

细节参见代码:

#include <cstdio>
#include <cstring>
#include <algorithm>
#include <iostream>
#include <string>
#include <vector>
#include <stack>
#include <ctime>
#include <bitset>
#include <cstdlib>
#include <cmath>
#include <set>
#include <list>
#include <deque>
#include <map>
#include <queue>
#define Max(a,b) ((a)>(b)?(a):(b))
#define Min(a,b) ((a)<(b)?(a):(b))
using namespace std;
typedef long long ll;
typedef long double ld;
const double eps = 1e-6;
const double PI = acos(-1);
const int mod = 1000000000 + 7;
const int INF = 0x3f3f3f3f;
// & 0x7FFFFFFF
const int seed = 131;
const ll INF64 = ll(1e18);
const int maxn = 100+10;
int sum[maxn],T,n,m,d[maxn],vis[maxn],kase = 0;
vector<int> g[maxn];
int dfs(int u, int fa) 
    int len = g[u].size();
    sum[u] = 1;
    for(int i = 0; i < len; i++) 
        int v = g[u][i];
        if(v == fa) continue;
        sum[u] += dfs(v, u);
    
    return sum[u];

int dp(int u, int fa) 
    int& ans = d[u];
    if(vis[u] == kase) return ans;
    vis[u] = kase;
    ans = 0;
    int len = g[u].size();
    if(len == 0) return -INF;

    for(int i = 0; i < len; i++) 
        int v = g[u][i];
        if(v == fa) continue;
        if(!(sum[v]&1)) ans = max(ans, ans+1);
        ans = max(ans, ans+dp(v, u));
    
    return ans;

int main() 
    scanf("%d%d", &n, &m);
    for(int i = 1; i <= m; i++) 
        int u, v;
        scanf("%d%d", &u, &v);
        g[u].push_back(v);
        g[v].push_back(u);
    
    ++kase;
    dfs(1, 1);
    int ans = dp(1, 1);
    printf("%d\\n", ans);
    return 0;



以上是关于HackerRank Even Tree(树dp)的主要内容,如果未能解决你的问题,请参考以下文章

hackerrank答案

Codeforces 161 D. Distance in Tree (树dp)

hdu5293 Tree chain problem 树形dp+线段树

HDU 6228 tree 简单思维树dp

HDOJ5534Partial Tree(树,背包DP)

在 ruby​​ 中解决 Hackerrank 的字谜解决方案