由于不是求最大的可拦截的HP值,而是要将最小值最大化,那么就需要分配每个子树用的钱数以达到最小值最大化

第一步解决如何分配钱使得结点u的子树中用了j元钱后可以拦截的HP最大,这就是变形的分组(依赖)背包,即枚举m元钱,在子树v用t元钱,在v之前的子树用j-t元钱

  用Max[v][j]数组记录u的前v个结点花j元钱可以拦截的最大HP,Max[v][j]=max{min( dp[v][t] , Max[v-i][j-t] )},第一维v可以压缩掉

第二步考虑结点u上建立什么炮塔,用Max数组来求出dp[u][j]即可

/*
给定一棵树,m块钱,每个结点上可以建造k种(价格price,攻击力power)防御塔
求可以阻拦的最大血量
dp[i][j]表示子树i中花费j元可以抵挡的怪物血量 */
#include<bits/stdc++.h>
using namespace std;
#define maxn 1050
struct Edge{int to,nxt;}edge[maxn<<];
struct node{int k,price[],power[];}p[maxn];
int n,m,head[maxn],tot,dp[maxn][],flag[maxn];
void init(){
tot=;
memset(head,-,sizeof head);
memset(flag,,sizeof flag);
}
void addedge(int u,int v){
edge[tot].to=v;edge[tot].nxt=head[u];head[u]=tot++;
}
void dfs(int u,int pre){
//init,每个点只能建立一个塔嘛
for(int j=m;j>=;j--)
for(int i=;i<=p[u].k;i++)
if(j>=p[u].price[i])
dp[u][j]=max(dp[u][j],p[u].power[i]); if(flag[u]==&&u!=)return;//叶子节点退出 for(int i=head[u];i!=-;i=edge[i].nxt){
int v=edge[i].to;
if(v!=pre)dfs(v,u);
} //Max[i][j]表示给前i个儿子花费j元时可以拦截的最大hp,可压成滚动数组
int Max[];
memset(Max,0x3f,sizeof Max);
for(int i=head[u];i!=-;i=edge[i].nxt){
int v=edge[i].to;
if(v==pre)continue;
for(int j=m;j>=;j--){//给子树v之前的子树用j元
int maxx=;
for(int t=;t<=j;t++)//给子树v用t元
maxx=max(maxx,min(dp[v][t],Max[j-t]));//找出最优的分配方式
Max[j]=maxx;//记录
}
} //最后Max数组表示给u的子树总共花i元可以拦截的最大HP
for(int j=m;j>=;j--)
for(int t=;t<=j;t++)//给子树花费t,给自己花费j-t元
dp[u][j]=max(dp[u][j],dp[u][j-t]+Max[t]);
//printf("%d\n",u);
//for(int i=1;i<=m;i++)
// printf("%d ",dp[1][i]);
}
int main(){
int t,u,v;
cin>>t;
while(t--){
init();
scanf("%d",&n);
for(int i=;i<n;i++){
scanf("%d%d",&u,&v);
addedge(u,v);
addedge(v,u);
flag[u]++;flag[v]++;
}
scanf("%d",&m);
for(int i=;i<=n;i++){
scanf("%d",&p[i].k);
for(int j=;j<=p[i].k;j++)
scanf("%d%d",&p[i].price[j],&p[i].power[j]);
}
memset(dp,,sizeof dp);
dfs(,);
printf("%d\n",dp[][m]);
}
}

hdu4044 依赖背包变形 好题!的更多相关文章

  1. 依赖背包变形——poj1947(经典)

    /*这题显然不适用依赖背包的优化,因为不能保证根是必选的,但是可以按照常规依赖背包的思路进行转移,即每次对一个儿子进行C^2的转移 还是树形的背包,dp[u][j]表示u的子树里,切割出一个大小为j的 ...

  2. 依赖背包变形(经典)——poj1155

    这个题用优化后的依赖背包做难以实现,所以用常规的泛化物品的和来做即可 每个节点的容量定义为这个节点下的叶子结点个数,dp[u][j]用来表示节点u下选取j个物品的最大收益,最后从m-0查询dp[1][ ...

  3. 依赖背包——cf855C好题

    比较裸的依赖背包,但是想状态还是想了好久 转移时由于边界问题,虽然可以倒序转移,但当容量为0|1的时候,由于有初始值的存在 很难再原dp数组上进行修改,所以额外用tmp数组来保存修改后的值 #incl ...

  4. HDU-4044 树形背包dp好题

    不会做,题解是参考网上的.感觉这道题是到好题,使得我对树形背包dp更了解了. 有几个注意的点,直接给出代码,题解以及注意点都在注释里了. #include<bits/stdc++.h> u ...

  5. 依赖背包变形——hdu4003

    思维性比较强,代码挺简单的,dp[u][j]表示在u子树下安排j个机器人,让其不回u 注意转移时的初始值 /* dp[u][j]为在子树u有j个机器人不回来 */ #include<bits/s ...

  6. hdu 1561 The more, The Better (依赖背包 树形dp)

    题目: 链接:点击打开链接 题意: 非常明显的依赖背包. 思路: dp[i][j]表示以i为根结点时攻击j个城堡得到的最大值.(以i为根的子树选择j个点所能达到的最优值) dp[root][j] = ...

  7. cf581F 依赖背包+临时数组 好题

    这题得加个临时数组才能做.. /* 给定一棵树,树节点可以染黑白,要求叶子节点黑白平分 称连接黑白点的边为杂边,求使得杂边最少的染色方 那么设dp[i][j][0|1]表示i子树中有j个叶子节点,i染 ...

  8. 【HDU 4276】The Ghost Blows Light(树形DP,依赖背包)

    The Ghost Blows Light Problem Description My name is Hu Bayi, robing an ancient tomb in Tibet. The t ...

  9. Codeforces Round #214 (Div. 2) C. Dima and Salad (背包变形)

    C. Dima and Salad time limit per test 1 second memory limit per test 256 megabytes input standard in ...

随机推荐

  1. MGR架构~ 整体性能架构的调优

    一 简介:MGR集群架构的调优二 过程:本文将从各个角度来具体阐述下三 硬件    1 硬件选择相同配置的服务器,磁盘,内存,cpu性能越高越好四 网络    1 0丢包和最好万兆网卡五 MGR本身  ...

  2. (7)Java数据结构--集合map,set,list详解

    MAP,SET,LIST,等JAVA中集合解析(了解) - clam_clam的专栏 - CSDN博---有颜色, http://blog.csdn.net/clam_clam/article/det ...

  3. 解决微信小程序使用switchTab跳转后页面不刷新的问题

    wx.switchTab({ url: '../index/index', success: function(e) { var page = getCurrentPages().pop(); if ...

  4. 【ARTS】01_16_左耳听风-20190225~20190303

    ARTS: Algrothm: leetcode算法题目 Review: 阅读并且点评一篇英文技术文章 Tip/Techni: 学习一个技术技巧 Share: 分享一篇有观点和思考的技术文章 Algo ...

  5. mysql select in 怎么优化

    2017年7月10日 22:36:54 星期一 原理: 把select where in 变换成 "where = " 或者 "where between and &qu ...

  6. FreeSWITCH异常原因总结

    最经在玩FreeSWITCH的时候,遇到很多的问题,特此总结一下,希望以后不要犯类似的错误了: 1.Client端无法注册,但是FS运行正常? 解决办法:查看防火墙是否关闭./etc/init.d/i ...

  7. 最新sublime text 3 注册码license分享(亲测有效)

    —– BEGIN LICENSE —– TwitterInc 200 User License EA7E-890007 1D77F72E 390CDD93 4DCBA022 FAF60790 61AA ...

  8. MinGW-w64非官方编译器集成安装包(很清楚)

    官方链接[编辑] MinGW 官方网站. SourceForge.net上的MinGW官方的下载站点(Win32系统). MinGW-w64官方的下载站点[编辑] MinGW-w64是2005年由On ...

  9. awk简单用法-(1)

    一.awk基本操作 awk指定多个分割符,分隔符中有:和空格,还有:和空格的组合,这个时候需要指定多个分隔符 -F'[ :]+',[ :]表示分隔符为:和空格,一个或者多个+号表示空格和:的组合也为一 ...

  10. .NET NPOI操作Excel 让单元格的内容换行

    HSSFWorkbook workbook = new HSSFWorkbook(); // 工作簿 ISheet sheet = workbook.CreateSheet("会员列表&qu ...