zoukankan      html  css  js  c++  java
  • 多重背包

    分析:                                                                                                                     

      每个数都可以用比它小的二进制数来表示,且每个数不重复使用   例如: 7 = 4 + 2 + 1; 9 = 8 + 1; 14 = 8 + 4 + 2  .....  // 1 2 4 8 16 32 64 

    然后就可以把给定的物品种数,分解成数量较小的多种物品,但是物品都是一样的,不影响后续01背包操作。

     1 #include<iostream>
     2 #include<algorithm>
     3 #include<cstring>
     4 #define LL long long
     5 using namespace std;
     6 
     7 int n, w, v, s, h;  //n为物品种类  w为背包容量  v为价值  s为体积  h为数量 
     8 int cnt;            //cnt为重新分组过后的总种类数 
     9 int value[800], size[800];
    10 int dp[50005];
    11 int main()
    12 {
    13     memset(dp,0,sizeof(dp));
    14     cin >> n >> w;
    15     for(int i = 0; i < n; i++){
    16         cin >> s >> v >> h;
    17         for(int j = 1; j <= h; j <<= 1){   //j*=2;
    18             value[cnt] = j*v;
    19             size[cnt++] = j*s;
    20             h -= j;
    21         }    
    22         if(h > 0){
    23             value[cnt] = h*v;
    24             size[cnt++] = h*s;
    25         }
    26     }
    27     for(int i = 0; i < cnt; i++)
    28         for(int j = w; j >= size[i]; j--)
    29             dp[j] = max(dp[j],dp[j-size[i]]+value[i]);
    30     cout << dp[w] << endl;
    31     return 0;
    32 } 

    注意点:

    • value数组和size数组要开大些! 具体看题目,因为重新分组过后,种类会变多,不止原来的n种
    •  1 for(int i = 0; i < n; i++){
       2     cin >> s >> v >> h;
       3     for(int j = 1; j <= h; j <<= 1){   //j*=2;
       4         value[cnt] = j*v;
       5         size[cnt++] = j*s;
       6         h -= j;
       7     }    
       8     if(h > 0){
       9         value[cnt] = h*v;
      10         size[cnt++] = h*s;
      11     }
      12 }

      二进制处理,不要忘了每处理一次后余下的h!!  比如,100 = 1 + 2 + 4 + 8 + 16 + 32 + 37;       (37就放在if(h > 0)处理)

    • 后续的01背包的第一重循环的 n 要换成 cnt, 也不能忘。

      

      好吧,好像都是我忘了的点,后来才恍然大悟的! 要细心呀!! 细心 

      总的来看,优化也不算难,理解就很简单。 可是,我自己看博客看了半天还是懵的,还是ff讲的比较好理解~ 哎呀哎呀 哈哈哈哈哈

      好啦,就到这里啦! over!

      对了对了,放个题,51nod 1086背包问题 V2

      代码就是上面的模板!  

      白白 ヾ(•ω•`)o 

  • 相关阅读:
    Spring入门
    排序算法【整理】
    C#并发解决(lock)
    Java poi导出word表格
    layui table checkbox默认选中
    Element table表尾合计行嵌入input
    Java接收带List的实体类
    Web SQL Database+mui上传视频
    Web SQL Database+mui上传图片
    mui 上传视频
  • 原文地址:https://www.cnblogs.com/JiaaaaKe/p/9465131.html
Copyright © 2011-2022 走看看