hdu 4091 Zombie’s Treasure Chest 贪心+枚举

题意:

输入背包体积n,绿宝石体积s1,价值v1,蓝宝石体积s2,价值v2,宝石数目无限,问背包里能放下的最大价值?

题解:

看过去很像完全背包,可数据很大(虽然没给出,也能猜到,不然太水了),所以不能用背包求。又只有两种物品,想到了贪心,将价值与体积比大(称为价值比)的优先放入。但体积限制,这样还不可以,还需要枚举减少价值比大的宝石个数,是否可以增大所求价值。又我们可以知道对于体积是m=lcm(s1,s2)背包,肯定全选价值比大的。所以至多只要枚举n-n/m+m的体积。如果小于这个值,存在大于m的空余,这个空余肯定用价值大的放置。

注意:

1.不够一个公倍数的时候,计算需要小心。。我就出错了。。

2.枚举的时候,跨度选择max(s1,s2),这个算是优化吧,没有的话会TLE



耗时:0MS/1000MS

#include <cstdio>
#include <cstring>
#include <cmath>
#include <iostream>
#include <algorithm>
using namespace std;
typedef __int64 LL;
LL gcd(LL a,LL b)
{
    return b==0?a:gcd(b,a%b);
}
LL lcm(LL a,LL b)
{
    return a/gcd(a,b)*b;
}
int main()
{
    LL n,s1,v1,s2,v2;
    LL T,tt=0;
    cin>>T;
    while(T--)
    {
        LL i,j,k,ans,p,q,m,num;
        cin>>n>>s1>>v1>>s2>>v2;
        m=lcm(s1,s2);
        num=n/m;
        if(num){num--;}
        if(v1*s2>=v2*s1)
        {
            num=m/s1*num;
            p=(n-num*s1)/s2;
            ans=num*v1+p*v2;
            if(s1>=s2)
            {
                for(i=num;i*s1<=n;i++)
                {
                    q=i*v1+(n-i*s1)/s2*v2;
                    if(q>ans)ans=q;
                }
            }
            else
            {
                for(i=p;i>=0;i--)
                {
                    q=i*v2+(n-i*s2)/s1*v1;
                    if(q>ans)ans=q;
                }
            }
        }
        else
        {
            num=m/s2*num;
            p=(n-num*s2)/s1;
            ans=num*v2+p*v1;
            if(s2>=s1)
            {
                for(i=num;i*s2<=n;i++)
                {
                    q=i*v2+(n-i*s2)/s1*v1;
                    if(q>ans)ans=q;
                }
            }
            else
            {
                for(i=p;i>=0;i--)
                {
                    q=i*v1+(n-i*s1)/s2*v2;
                    if(q>ans)ans=q;
                }
            }
        }
        cout<<"Case #"<<++tt<<": "<<ans<<endl;
    }
    return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值