zoukankan      html  css  js  c++  java
  • 【动态规划】多重背包

    贵有恒,何必三更起五更眠;最无益,莫过一日曝十日寒。

    【动态规划】多重背包

    时间限制: 1 Sec  内存限制: 64 MB
    提交: 5  解决: 5
    [提交][状态][讨论版]

    题目描述

    张琪曼:“魔法石矿里每种魔法石的数量看起来是足够多,但其实每种魔法石的数量是有限的。”

    李旭琳:“所以我们需要改变装包策略啦。”

    现有N(N≤10)种魔法石和一个容量为V(0<V<200)的背包。第i种魔法石最多有n[i]件可用,每个占用的空间是c[i],价值是w[i]。全部物品总数不超过50。求解将哪些魔法石装入背包可使这些物品的容量总和不超过背包容量,且价值总和最大。

    输入

    第一行为两个数字,即V和N。以下N行为每种物品的空间,价值和数量。

    输出

    最大价值总和。

    样例输入

    8 2
    2 100 4
    4 100 2
    

    样例输出

    400


    #include <iostream>
    #include <cstring>
    #define INF 0x3f3f3f3f
    using namespace std;
    int f[222],v[11],w[11],num[11];
    int n,m;
    
    //m背包的总容量、v物品的体积、w物品的价值
    void OneZeroPack(int m,int v,int w)  //0-1背包
    {
        for(int i=m;i>=v;i--)
            f[i]=max(f[i],f[i-v]+w);
    }
    
    //m背包的总容量、v物品的体积、w物品的价值
    void CompletePack(int m,int v,int w)  //完全背包
    {
        for(int i=v;i<=m;i++)
            f[i]=max(f[i],f[i-v]+w);
    }
    
    //m背包的总容量、v物品的体积、w物品的价值、num物品的数量
    void MultiplePack(int m,int v,int w,int num)//多重背包
    {
        if(v*num>=m)
        {
            CompletePack(m,v,w);
            return ;
        }
        int k=1;
        for(k=1;k<=num;k<<=1)
        {
            OneZeroPack(m,k*v,k*w);
            num=num-k;
        }
        if(num)
            OneZeroPack(m,num*v,num*w);
    }
    
    int main()
    {
        while(cin>>m>>n)
        {
            for(int i=0;i<n;i++)
                cin>>v[i]>>w[i]>>num[i];
            memset(f,0,sizeof(f));
            for(int i=0;i<n;i++)
            {
                MultiplePack(m,v[i],w[i],num[i]);
            }
            cout<<f[m]<<endl;
        }
        return 0;
    }
     
  • 相关阅读:
    真爱 vs. 种姓:新一代印度人的婚恋观
    美国司法部解禁guns打印技术
    特朗普访英,吃瓜群众却只想看《真爱至上》
    Semaphore(信号量)
    RLock(递归锁)
    用python编写九九乘法表
    php传值和传引用的区别
    post请求的header
    Content-type详解
    thinkphp5 学习笔记
  • 原文地址:https://www.cnblogs.com/asuml/p/5733720.html
Copyright © 2011-2022 走看看