HDOJ 1561 The more, The Better(树形DP)

来源:互联网 发布:淘宝店铺模板什么格式 编辑:程序博客网 时间:2024/05/22 03:11

在树上做背包。

学到一点:如果想要处理的是树,但是题目中给的是森林的话,可以加一个总的根结点。

A 掉 1011 之后这题就比较顺利的 1A 了。

代码:

#include <cstdio>#include <cstring>#include <algorithm>using namespace std;const int maxn = 220, inf = 0x3f3f3f3f;int n, m;int fr[maxn * 2], to[maxn * 2], head[maxn], next[maxn * 2];int val[maxn], dp[maxn][maxn];bool vis[maxn];bool read(){    if(!(~scanf("%d%d", &n, &m) && (n || m)))        return 0;    int ecnt = 0;    memset(head, -1, sizeof(head));    //memset(isrt, false, sizeof(isrt));    for(int i = 1; i <= n; i++) {        int a;        scanf("%d%d", &a, &val[i]);        fr[ecnt] = a;///0        to[ecnt] = i;        next[ecnt] = head[a];        head[a] = ecnt;        ecnt++;    }    return 1;}void dfs(int cur){    vis[cur] = true;    for(int i = 1; i <= m+1; i++) dp[cur][i] = val[cur];    for(int i = head[cur]; ~i; i = next[i]) {        int tar = to[i];        if(vis[tar]) continue;        dfs(tar);        for(int j = m+1; j > 0; j--)            for(int k = 1; k < j; k++)                dp[cur][j] = max(dp[cur][j], dp[cur][j-k] + dp[tar][k]);    }}void solve(){    memset(dp, 0, sizeof(dp));    memset(vis, false, sizeof(vis));    dfs(0);    printf("%d\n", dp[0][m+1]);}int main(){    while(read()) {        solve();    }    return 0;}


0 0