这是自己第一道背包上树形结构问题,不是很理解这个概念的可以先看看背包九讲

自己第一次做,看了一下别人的思路,结合着对简单背包问题的求解方式自己一次AC了还是有点小激动的

题目大意是:

攻克m个城市,每个城市都有对应数量的宝贝,攻克某一个城市必须保证其对应的某一个特定城市已经被攻克,希望得到最多数量的宝贝

很容易根据题目画出一个对应关系的树形结构,每个节点都有一个对应的宝物的数量

我们用dp[i][j]存 i 号节点它下方子树中 有 j 个城市被攻克时得到的宝物最大数量 , 此时的 i 号是没有被攻克的!

然后通过dfs自底向上更新

 /*
总的u下方子树攻克了j个城市,为当前v姿势分配k个城市攻克
添加当前v包含了攻克k-1个子树的城市,要添加子树v必须
同时保证v被攻克,所以加上的是dp[v][k-1] + val[v]
*/
for(int j = m ; j>= ; j--){
for(int k = j ; k> ; k--){
dp[u][j] = max(dp[u][j] , dp[u][j-k] + dp[v][k-] + val[v]);
}
}

这里可以理解为当根节点u下方有 j 个城市被攻克时, 若有 k 个城市的攻克来自v的子树, 那么v必然要被攻克 , val[v],不然其下方的城市不能攻克

除去v还有 k -1个v节点对应子树中的城市要攻克 ,也就是 dp[v][k-1]

 #include <cstdio>
#include <cstring>
#include <iostream>
using namespace std;
const int N = ; int dp[N][N] , val[N] , first[N] , k; struct Edge{
int y , next;
}e[N]; void add_edge(int x , int y)
{
e[k].y = y , e[k].next = first[x];
first[x] = k++;
} void dfs(int u , int m)
{
for(int i=first[u] ; i!=- ; i=e[i].next){
int v = e[i].y;
dfs(v , m);
/*
总的u下方子树攻克了j个城市,为当前v姿势分配k个城市攻克
添加当前v包含了攻克k-1个子树的城市,要添加子树v必须
同时保证v被攻克,所以加上的是dp[v][k-1] + val[v]
*/
for(int j = m ; j>= ; j--){
for(int k = j ; k> ; k--){
dp[u][j] = max(dp[u][j] , dp[u][j-k] + dp[v][k-] + val[v]);
}
}
}
} int main()
{
// freopen("a.in" , "r" , stdin);
int n , m , a , b;
while(scanf("%d%d" , &n , &m) , n||m)
{
memset(first , - , sizeof(first));
k = ;
for(int i= ; i<=n ; i++)
{
scanf("%d%d" , &a , &b);
add_edge(a , i);
val[i] = b;
}
memset(dp , , sizeof(dp));
dfs( , m); printf("%d\n" , dp[][m]);
}
return ;
}

HDU 1561 树形DP背包问题的更多相关文章

  1. HDU 1561 树形DP入门

    The more, The Better Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Oth ...

  2. HDU 1561 树形DP(入门)

    题目链接:  HDU 1561 The more, The Better #include <iostream> #include <cstdio> #include < ...

  3. HDU 1561 (树形DP+背包)

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=1561 题目大意:从树根开始取点.最多取m个点,问最大价值. 解题思路: cost=1的树形背包. 有 ...

  4. hdu 1561(树形dp)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1561 思路:dp[u][i]表示以u为根的树选了i个子节点. #include<iostream ...

  5. hdu 1561 树形dp+分组背包

    题意:就是给定n个点,每个地点有value[i]的宝物,而且有的宝物必须是另一个宝物取了才能取,问取m个点可以获得的最多宝物价值. 一个子节点就可以返回m个状态,每个状态表示容量为j(j<=m) ...

  6. hdu 1561 树形DP n个选m个价值最大

    http://acm.hust.edu.cn/vjudge/problem/18068 #include <iostream> #include <string> #inclu ...

  7. hdu 4123 树形DP+RMQ

    http://acm.hdu.edu.cn/showproblem.php? pid=4123 Problem Description Bob wants to hold a race to enco ...

  8. HDU 1520 树形dp裸题

    1.HDU 1520  Anniversary party 2.总结:第一道树形dp,有点纠结 题意:公司聚会,员工与直接上司不能同时来,求最大权值和 #include<iostream> ...

  9. HDU 2196树形DP(2个方向)

    HDU 2196 [题目链接]HDU 2196 [题目类型]树形DP(2个方向) &题意: 题意是求树中每个点到所有叶子节点的距离的最大值是多少. &题解: 2次dfs,先把子树的最大 ...

随机推荐

  1. 【WIP_S2】递归

    创建: 2018/01/14    递归  定义  自己召唤自己  通用形式  if (基本情况A的处理) {     ...     return 值A  } else if (基本情况B的处理) ...

  2. bzoj 2427: [HAOI2010]软件安装【tarjan+树形dp】

    一眼最大权闭合子图,然后开始构图,画了画之后发现我其实是个智障网络流满足不了m,于是发现正确的打开方式应该是一眼树上dp 然后仔细看了看性质,发现把依赖关系建成图之后是个奇环森林,这个显然不能直接dp ...

  3. 【Tair】淘宝分布式NOSQL框架:Tair

    Tair是淘宝的一个开源项目,它是一个分布式的key/value结构数据的解决方案. 一.基本组成 作为一个分布式系统,Tair由一个中心控制节点(config server)和一系列的服务节点(da ...

  4. MySQL客户端导入数据库脚本,字段值出现乱码解决方法

    解决方法1:在MySql安装目录下找到my.ini,将[mysql]下的default-character-set=latin1改为default-character-set=utf8,保存,然后重启 ...

  5. 关于java的print()

    print方法是类PrintStream的方法成员,而System类有一个static的PrintStream类型的属性成员,名叫out,我们平时写的System.out.print("he ...

  6. 微信开发解决if...else..的臃肿

    开发中难以避免if...else (switch case ),大量的if...else 让代码可读性低...难以维护 无论是接手别人的代码还是自己写的代码,因为开发周期短可能就往往忽略了这一点. 久 ...

  7. python--12、pymysql模块

    安装 pip3 install pymysql 使用方法(示例表为用户注册信息表): import pymysql user=input('username: ').strip() pwd=input ...

  8. IDEA 导入maven项目,显示:nothing to show

    问题描述: IDEA 导入maven项目,import project,默认下一步,直到Select Maven projects to import界面无选项,提示:nothing to show ...

  9. React Native 出现红屏幕报连接服务失败

    最近移动项目组在本人的带领下切换进React Native开发应用,之前没接触过,用了几周之后,发现也就那么回事吧,小玩具项目用用还是可以的.今天Android小姑娘在Windows下出问题解决不了, ...

  10. 微信小程序组件解读和分析:三、swiper滑块视图

    swiper滑块组件说明: 滑块视图容器,用于展示图片,可以通过用户拖拽和设置自动切换属性控制图片的切换   组件的使用示例的运行效果如下: 下面是WXML代码: [XML] 纯文本查看 复制代码 ? ...