夏季特惠

题目描述

Steam 2019年夏季促销开始了!

⼩Y同学决定⼊⼿⼀些游戏,⼩Y同学⼀共有x元的预算,该平台上所有的n个游戏均有折扣,标号为i的游戏的原价ai元,现价只要bi元(也就是说该游戏可以优惠ai−bi元,每款游戏最多只能购买⼀次),并且⼩Y同学购买该游戏能获得快乐值为wi。

由于优惠的存在,⼩Y作为剁⼿党可能做出⼀些冲动消费导致最终买游戏的总费⽤超过预算,但只要满足获得的总优惠金额不低于超过预算的总金额,那在⼩Y同学⼼理上就不会觉得吃亏(买到就是赚到!真⾹!)。现在⼩Y希望在⼼理上不觉得吃亏的前提下,获得尽可能多的快乐值。
输入格式
第⼀⾏包含两个数n和x。接下来n⾏包含每个游戏的信息,原价ai,现价bi,能获得的快乐值为wi。
输出格式
输出⼀个数字,表⽰⼩Y同学能获得的最⼤快乐值。

思路

我们输入ai,bi,wi时。
如果2*bi-ai<=0,这件物品我们就必须要,为什么?因为我们买了这个物品的话,我们不亏,也就是我们得到的优惠一定大于或等于使用的钱,对后面的选择完全没有影响,我们买了的话,有可能会有得赚,何乐而不为呢?

剩下的物品,就直接一个01背包。

代码

#include <bits/stdc++.h>
using namespace std;
long long m,n,len,f[1000005],ans;
struct node{ long long y,z; }a[505];

int main() {
	scanf("%lld %lld",&n,&m);
	for(long long i=1,ai,bi,ci;i<=n;i++) {
		scanf("%lld %lld %lld",&ai,&bi,&ci);
		long long vi=bi*2-ai;
		if(vi<=0) m-=vi,ans+=ci;
		else a[++len].y=vi,a[len].z=ci;
	}
	for(long long i=1;i<=len;i++) {
		for(long long j=m;j>=a[i].y;j--) {
			if(f[j-a[i].y]+a[i].z>f[j])
				f[j]=f[j-a[i].y]+a[i].z;			
		}
	}
	printf("%lld",f[m]+ans);
	return 0;
}
原文地址:https://www.cnblogs.com/sxqn/p/13769929.html