zoukankan      html  css  js  c++  java
  • (暴力)UVA

    题意:有一个容量为n的背包,有两种宝物,体积分别为S1,S2;价值为V1,V2。这两种宝物有无数种,现在向背包中塞宝物,问最多能装多少价值。


    分析:可以很容易想到这个代码

    for (int i = 0; i <= n / max(s1,s2); i++) {
                tmp = i * v1;
                ans = max(ans, tmp + ((n - i * s1) / s2) * v2);
    }

    但是,如果max(s1,s2)很小的话,就会瞬间爆炸。

    比如n有1073741824,但是max(s1,s2)==2,循环就到了亿级。

    所以可以在考虑max(s1,s2)比较小的时候换一种暴力的方式。

    直接考虑两种宝物性价比哪个高,暴力那个性价比高的即可。

    if (s1 <= 100000) {
        if (s1 * v2 > s2 * v1) //第二个宝物性价比第一个宝物高
    {
    for (int i = 0; i < s2; i++) { tmp = i * v1; ans = max(ans, tmp + ((n - i * s1) / s2) * v2); } } else for (int i = 0; i < s1; i++) { tmp = i * v2; ans = max(ans, tmp + ((n - i * s2) / s1) * v1); } } }

    第二个宝物性价比比第一个宝物高时:

    其实就是遍历取第一种宝物数量的暴力,可能取0个、1个、2个....s2-1个,这是未知的,所以需要通过暴力跑出来。

    为什么不需要s2个,因为如果第一种取s2个,因为第二个宝物的性价比比第一个宝物高,所以取s2个第一宝物还不如取s1个第二宝物。

    反之类似。


    代码:

     1 #include <set>
     2 #include <map>
     3 #include <list>
     4 #include <cmath>
     5 #include <queue>
     6 #include <vector>
     7 #include <bitset>
     8 #include <string>
     9 #include <cctype>
    10 #include <cstdio>
    11 #include <cstring>
    12 #include <cstdlib>
    13 #include <iostream>
    14 #include <algorithm>
    15 
    16 using namespace std;
    17 
    18 typedef long long ll;
    19 typedef unsigned long long ull;
    20 #define inf (0x3f3f3f3f)
    21 #define lnf (0x3f3f3f3f3f3f3f3f)
    22 #define eps (1e-8)
    23 int sgn(double a) {return a < -eps ? -1 : a < eps ? 0 : 1;}
    24 
    25 //--------------------------
    26 
    27 
    28 
    29 int t;
    30 ll s1, v1, s2, v2;
    31 ll n;
    32 
    33 void solve() {
    34     scanf("%d", &t);
    35     int s = 0;
    36     while (t--) {
    37         scanf("%lld%lld%lld%lld%lld", &n, &s1, &v1, &s2, &v2);
    38         if (s1 < s2) {
    39             swap(s1, s2);
    40             swap(v1, v2);
    41         }
    42         ll tmp;
    43         ll ans = 0;
    44         if (s1 <= 100000) {
    45             if (s1 * v2 > s2 * v1) {
    46                 for (int i = 0; i < s2; i++) {
    47                     tmp = i * v1;
    48                     ans = max(ans, tmp + ((n - i * s1) / s2) * v2);
    49                 }
    50             } else {
    51                 for (int i = 0; i < s1; i++) {
    52                     tmp = i * v2;
    53                     ans = max(ans, tmp + ((n - i * s2) / s1) * v1);
    54                 }
    55             }
    56             printf("Case #%d: %lld
    ", ++s, ans );
    57             continue;
    58         }
    59         for (int i = 0; i <= n / s1; i++) {
    60             tmp = i * v1;
    61             ans = max(ans, tmp + ((n - i * s1) / s2) * v2);
    62         }
    63         printf("Case #%d: %lld
    ", ++s, ans );
    64     }
    65 
    66 }
    67 
    68 
    69 
    70 int main() {
    71 
    72 #ifndef ONLINE_JUDGE
    73     freopen("1.in", "r", stdin);
    74     freopen("1.out", "w", stdout);
    75 #endif
    76     //iostream::sync_with_stdio(false);
    77     solve();
    78     return 0;
    79 }
  • 相关阅读:
    ConCurrent并发包
    volitale最经典理解
    java中关于volatile的理解疑问?
    一直对zookeeper的应用和原理比较迷糊,今天看一篇文章,讲得很通透,分享如下(转)
    架构师成长之路
    rocketmq,zookeeper,redis分别持久化的方式
    rocketmq持久化方式
    源码主干分支开发四大模式
    HDU 4876 ZCC loves cards(暴力剪枝)
    webView用法小结
  • 原文地址:https://www.cnblogs.com/tak-fate/p/6132098.html
Copyright © 2011-2022 走看看