SDUT3303 来发背包开开胃(模拟背包) ,DFS

本文介绍了一个经典的背包问题,探讨了如何在有限预算下购买多种商品以实现最大总质量的目标。通过使用暴力搜索的方法解决了该问题,并提供了两种不同的C++代码实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

来发背包开开胃

Time Limit: 1000ms   Memory limit: 65536K  有疑问?点这里^_^

题目描述

现有n种商品,每种商品有Si件,每种商品的价格和质量分别为PiMi。你现在有钱V,问能购买的商品的总质量最大为多少。

输入

 多组输入。 对于每组输入:

第一行两个整数nV(1 <= n <= 3,1 <= V <= 1,000,000,000)。

接下来的n行,每行三个整数SiPiMi,分别代表第i种物品的数量,价格与质量(1 <= Si <= 100,1 <= Pi <= 1,000,000,000 , 1 <= Mi <= 1,000,000,000)

输出

 对于每组数据,输出一个整数代表答案。

示例输入

1 1010 1 10

示例输出

100

提示

 此题数太大,不能用背包dp[10000000...],就算用map,也会因为从0初始化化到10亿而超时;
但数量少,可暴力,可DFS..
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>

using namespace std;

int main()
{
	int n;
	long long v,sum=-1,ans,s[4],m[5],p[5];
	while(~scanf("%d%lld",&n,&v))
	{
		sum=-1;
		memset(s,0,sizeof(s));
		memset(p,0,sizeof(p));
		memset(m,0,sizeof(m));

		for(int i=0;i<n;i++)
			scanf("%lld%lld%lld",&s[i],&p[i],&m[i]);
			
		for(int i=0;i<=s[0];i++)       //暴力模拟背包
			for(int j=0;j<=s[1];j++)
				for(int k=0;k<=s[2];k++)
				{
					if(v<i*p[0]+j*p[1]+p[2]*k)
					 continue;
					ans=i*m[0]+j*m[1]+m[2]*k;
					if(sum<ans)
						sum=ans;
				}
			printf("%lld\n",sum);
	}
}
 


#include<iostream>
#include<cstring>
#include<cstdio>

using namespace std;
long long int n,v;
long long sum=-1;
long long int m[1000],p[1000],s[1000];
int vis[5],tt=0;
int DFS(int i,long long int v,long long int ans,int num)
{
    if(v<0)     
        return 0;
    if(i>n)        //种类
        return 0;
    if(num>tt)     //个数不能超过总个数
        return 0;
    if(ans>sum)
    {
        sum=ans;
        return 0;
    }
    for(int j=0; j<=s[i]; j++)
    {
        if(v-p[i]*j>=0)
        {
            DFS(i+1,v-p[i]*j,ans+m[i]*j,num+j);

        }
    }
}
int main()
{
    while(~scanf("%lld%lld",&n,&v))
    {
        tt=0;
        for(int i=0; i<n; i++)
        {
            scanf("%lld%lld%lld",&s[i],&p[i],&m[i]);
            tt+=s[i];
        }
        memset(vis,0,sizeof(vis));
        sum=0;
        DFS(0,v,0,0);
        printf("%lld\n",sum);
    }
}



 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值