codeforces 526C Om Nom and Candies 分两种情况暴力枚举

题目链接:

http://codeforces.com/problemset/problem/526/C

题意:

给你一个容量为V的背包,有两种物品,每种都有无穷多个。

第一种物品的体积为v1,价值为w1

第一种物品的体积为v2,价值为w2

输入V,w1,w2,v1,v2.计算这个背包最多能放价值多少的物品。

数据范围:

V,w1,w2,v1,v2 都在1到10^9范围内。

题解:

如果按照完全背包的做法,用dp来做,复杂度O(nV),n为物品数量,这道题物品数量为2,但是背包容量V很大。dp会超时。

正确思路是:
分两种情况讨论:

1.如果 max(v1,v2)>=根号V。

假设v1>=根号V.那么这个背包全放物品1最多只能放根号V个。物品1可以放0到根号V个。我们只需要暴力枚举物品1的个数,就可以算出来物品2的个数,算出来背包所能放的最大价值。ans=max(i*w1,(V-i*v1)/v2*w2).时间复杂度O(根号V);

2.如果 max(v1,v2)<根号V。

 我们假设w1/v1<w2/v2(实际不满足这个条件可以交换这两个物品),也就是物品2的性价比更高。

物品1体积为v1,物品2体积为v2。那么v2个物品1和v1个物品2的体积相等。因为物品2的性价比比物品1高,所以最优情况下物品1最多放v2个。因为v2个物品1换成v1个物品2体积没变,价值更高了。枚举物品1的个数就可以算出来背包能放得最大价值了。时间复杂度O(根号v2). v2<根号V

所以最坏的情况下复杂度是O(根号V).

代码

#include<algorithm>
#include <iostream>
#include<cstring>
#include <cstdio>
using namespace std;
typedef long long ll;
const int maxn=5e5+5;
int main(){
    ll v,a1,b1,a2,b2;
    cin>>v>>a1>>a2>>b1>>b2;
    ll x=max(b1,b2);
    if(x*x>=v){
        if(b1<b2) swap(a1,a2),swap(b1,b2);
        ll ans=0;
        for(int i=0;i<=v/b1;i++){
            ans=max(ans,i*a1+(v-i*b1)/b2*a2);
        }
        cout<<ans<<endl;
    }else{
        if(1.0*a1/b1>1.0*a2/b2){
            swap(a1,a2),swap(b1,b2);
        }
        ll ans=0;
        for(int i=0;i<b2;i++){
            ans=max(ans,i*a1+(v-i*b1)/b2*a2);
        }
        cout<<ans<<endl;
    }
    return 0;
}

 

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值