P1064 [NOIP2006 提高组] 金明的预算方案

文章讲述了在01背包问题中,考虑了主物品和附物品的依赖关系的动态规划解题方法,通过转移方程详细描述了不同状态下的决策过程。给出了一段使用C++编写的AC代码示例。
摘要由CSDN通过智能技术生成

01 01 01背包的变式,有依赖的背包题
题目链接

思路

考虑到我们一般的 01 01 01背包题,动态转移方程成立条件为:若背包容量能容纳该物品,则判断取最大,否则跳过
而该题有多种状态,对于每一种物品(主物品+配套的附物品)
不取主物品
取主物品不取附属物品
取主物品和附属物品 1 1 1,不取附属物品 2 2 2(如果有的话)
取主物品和附属物品 2 2 2,不取附属物品 1 1 1(如果有的话)
取主物品和附属物品 1 , 2 1,2 1,2(如果有的话)
然后打上 01 01 01背包的板子就行了

ACcode

#include<bits/stdc++.h>

using namespace std;

const int M = 3e5 + 9;
int dp[M];
int cv[M], cw[M];
int fv[M][7], fw[M][7];

int main()
{
    ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
    int n, m;cin >> n >> m;
    int a, b, c;
    for (int i = 1;i <= m;i++) {
        cin >> a >> b >> c;
        if (!c) {
            cv[i] = a;
            cw[i] = a * b;
        }
        else {
            fv[c][0]++;
            fv[c][fv[c][0]] = a;
            fw[c][fv[c][0]] = b * a;
        }
    }
    for (int i = 1;i <= m;i++) {
        for (int j = n;j >= cv[i];j--) {
            dp[j] = max(dp[j], dp[j - cv[i]] + cw[i]);
            if (j >= cv[i] + fv[i][1])dp[j] = max(dp[j], dp[j - cv[i] - fv[i][1]] + cw[i] + fw[i][1]);
            if (j >= cv[i] + fv[i][2])dp[j] = max(dp[j], dp[j - cv[i] - fv[i][2]] + cw[i] + fw[i][2]);
            if (j >= cv[i] + fv[i][1] + fv[i][2])dp[j] = max(dp[j], dp[j - fv[i][1] - cv[i] - fv[i][2]] + cw[i] + fw[i][1] + fw[i][2]);
        }
    }
    cout << dp[n];
    return 0;
}

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值