Consumer (有依赖的背包)

题目大意:

给你一些物品,每个物品有自己的花费和价值,每个物品 都有相对应的箱子, 如果你想要买这个物品,你就需要先买这个箱子(依赖),求 n个箱子花费 t 能获得的最大价值

思路:

dp[i][j]  代表在 i 个箱子花费 j 能获得的最大价值

我们需要优先对箱子进行处理,处理完之后其他的都和 01背包一样了

具体的看代码注释吧

int dp[55][100010];
int n,t,box,num;
int main ()
{
    int i,j,k;
    while(scanf("%d %d",&n,&t)!=EOF)
    {
         memset(dp,0,sizeof(dp));//初始化背包
        for(i=1;i<=n;i++)
        {
            scanf("%d %d",&box,&num);
            for (int j=0; j<=box;j++) //对盒子的处理(即依赖)
                dp[i][j] = -1;
            for(k=t;k>=box;k--)
                dp[i][k]=dp[i-1][k-box]; //先让每组数据拿到上组的状态

           //下列操作先算出我需要该组物品(盒子)
            for(j=0;j<num;j++)
            {
                int c,w;
                scanf("%d %d",&c,&w);
                for(k=t;k>=c;k--)
                {
                    if(dp[i][k-c]!=-1)
                        dp[i][k]=max(dp[i][k],dp[i][k-c]+w);
                }
            }
            //取和不取的比较算出最大价值
            for(j=0;j<=t;j++)
            {
                dp[i][j]=max(dp[i-1][j],dp[i][j]);
            }
        }
        printf("%d\n",dp[n][t]);
    }
    return 0;
}

原文地址:https://www.cnblogs.com/-Ackerman/p/12264623.html

时间: 2024-11-12 17:54:35

Consumer (有依赖的背包)的相关文章

hdu 3449 Consumer (依赖01背包)

题目: 链接:点击打开链接 题意: 思路: dp[i][j]表示前i个箱子装j钱的材料可以得到的最大价值. 代码: #include<iostream> #include<cstdio> #include<cstring> using namespace std; #define MAXN 100010 int dp[55][MAXN]; int main() { //freopen("input.txt","r",stdin);

C. Coin Troubles 有依赖的背包 + 完全背包变形

http://codeforces.com/problemset/problem/283/C 一开始的时候,看着样例不懂,为什么5 * a1 + a3不行呢?也是17啊 原来是,题目要求硬币数目a3 > a4 > a2,那么,不选的话,是不合法的.就是0.0.0这样是不合法的,因为a3 = a4了. 那么就可以知道, a3起码都要选两个了. 那么怎么维护这个关系呢?,思路是有依赖的背包,需要a3的数目比a4的多,就可以把a4那件物品变成a3 + a4 那么每一次选择的时候,就隐含地选了一件a3

HAOI2010 软件安装 有依赖的背包DP

题目描述 现在我们的手头有N个软件,对于一个软件i,它要占用Wi的磁盘空间,它的价值为Vi.我们希望从中选择一 些软件安装到一台磁盘容量为M计算机上,使得这些软件的价值尽可能大(即Vi的和最大). 但是现在有个问题:软件之间存在依赖关系,即软件i只有在安装了软件j(包括软件j的直接或间接依赖)的情况下才能正确工作(软件i依赖软件j).幸运的 是,一个软件最多依赖另外一个软件.如果一个软件不能正常工作,那么它能够发挥的作用为0. 我们现在知道了软件之间的依赖关系:软件i依赖软件Di.现在请你设计出

树形依赖的背包 树形dp

树形DP有一个独特的优化,就是通过递归,枚举目前有效的元素个数,求dp[ i ][ j ] (表示 选取以i为根的子树中有选取j个元素的最大取值) (搭配 siz 数组表示当前该节点的总共子孙数) 1.hdu1561(树形依赖背包裸题) 注意 siz 数组的运用,以及 u 点选择的节点数时要逆向枚举,就像01背包 复杂度看似O(n^3),实际是 O( n^2 ) 左右. #include <iostream> #include <cstdio> #include <cstri

有依赖的背包

问题描述: 解法: 这种树形的结构我们首先很容易去想到 树形dp ,但是和 树形dp 不一样的地方在于它选一个节点的话还有附加条件(也就是依赖关系) 我们对于每一个节点可以把它看成一个分组背包 dp[i][j] 代表 选第 i 个节点 背包容量为 j 的时候 背包的最大价值 我们可以先采取 树形dp 的方法去更新叶子节点,然后更新父亲节点 更新父亲节点的状态转移方程也很好想: dp[i][j] = max(dp[i][j],dp[son][k]+dp[i][j-k]) int n,m; int

P1064 金明的预算方案(01背包||有依赖的背包(待解决))

直接01背包硬刚,虽然容易理解,但是完全不适合附件多的情况 1 /* 2 1.只选主件 3 2.选主件和附件1 4 3.选主件和附件2 5 4.选主件和附件1.2 6 */ 7 #include <iostream> 8 #include<string> 9 #include<cstdio> 10 #include<cmath> 11 #define ll long long 12 using namespace std; 13 int V[70][3],P

金明的预算方案————有依赖的背包

题目描述 金明今天很开心,家里购置的新房就要领钥匙了,新房里有一间金明自己专用的很宽敞的房间.更让他高兴的是,妈妈昨天对他说:“你的房间需要购买哪些物品,怎么布置,你说了算,只要不超过N元钱就行”.今天一早,金明就开始做预算了,他把想买的物品分为两类:主件与附件,附件是从属于某个主件的,下表就是一些主件与附件的例子: 主件 附件 电脑 打印机,扫描仪 书柜 图书 书桌 台灯,文具 工作椅 无 如果要买归类为附件的物品,必须先买该附件所属的主件.每个主件可以有0个.1个或2个附件.附件不再有从属于

背包九讲(转载)

转载 背包问题 //0 1背包 #include<iostream> #include<stdio.h> #include<string.h> using namespace std; int main() { int i,j,n,v,f[1100],w[1100],p[1100]; scanf("%d",&t); while(t--) { memset(f,0,sizeof(f)); scanf("%d%d",&

HDU 1561 ——The more, The Better(有依赖的树形DP)

题目分析: 攻占城堡所能获得的最多宝物,但是有个限制,要想攻占某个城堡前必须先攻占另一个城堡 思路: 建图,新建一个根节点为0,那么题目就变为要想取得子节点必须先取得它的父亲节点 今天为了解决这个问题,看了下背包九讲中的有依赖的背包,刷了道模板题. 大概思路是:要想取得附件必须先取主件,主件要么取,要么不取,取得话要怎么分配给附件,用01背包处理附件,然后再把每个主件分组背包 树形的依赖主要是附件是个集合,附件还有附件.森林的概念 根据DP的思想,我们先dfs到叶,01背包操作 即可.只是每次d