CF(01背包+贪心) 第八届山东省省赛

CF

Time Limit: 1000 ms Memory Limit: 65536 KiB

Problem Description

LYD loves codeforces since there are many Russian contests. In an contest lasting for T minutes there are n problems, and for the ith problem you can get aiditi points, where ai indicates the initial points, di indicates the points decreased per minute (count from the beginning of the contest), and ti stands for the passed minutes when you solved the problem (count from the begining of the contest).
Now you know LYD can solve the ith problem in ci minutes. He can't perform as a multi-core processor, so he can think of only one problem at a moment. Can you help him get as many points as he can?

Input

The first line contains two integers n,T(0≤n≤2000,0≤T≤5000).
The second line contains n integers a1,a2,..,an(0<ai≤6000).
The third line contains n integers d1,d2,..,dn(0<di≤50).
The forth line contains n integers c1,c2,..,cn(0<ci≤400).

Output

Output an integer in a single line, indicating the maximum points LYD can get.

Sample Input

3 10
100 200 250
5 6 7
2 4 10

Sample Output

254

可以推出状态转移方程:dp[i]=max(dp[i], dp[i-ci]+ai-i*di);i表示已经花费了i时间;(在背包中i表示是已经使用的容积)

现在有个问题c, d的顺序的变化, 会对上式产生影响, 那么究竟什么样的应该在前?

设现在有两个问题, 属性分别为a1, d1, c1;  a2, d2, c2;

先做第一个得 p1=a1-d1*c1+a2-(c1+c2)*d2=a1+a2-(d1*c1+d2*c2+d2*c1);

先做第二个得 p2=a2-d2*c2+a1-(c1+c2)*d1=a1+a2-(d1*c1+d2*c2+d1*c2);

若p1>p2此时先做第一个问题, 化简不等式得:d1*c2>d2*c1;

所以我们应按这种顺序排序后在进行01背包;

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <cmath>
using namespace std;
int dp[5100];
struct node{
	int a, d, c;
}p[2100];
int n, T;
bool cmp(node x, node y){
	return x.d*y.c>y.d*x.c;
}
int main(){
	scanf("%d%d", &n, &T);
	for(int i=1; i<=n; i++){
		scanf("%d", &p[i].a);
	}
	for(int i=1; i<=n; i++){
		scanf("%d", &p[i].d);
	}
	for(int i=1; i<=n; i++){
		scanf("%d", &p[i].c);
	}
	sort(p+1, p+n+1, cmp);
	int ans=0;
	for(int i=1; i<=n; i++){
		for(int j=T; j>=p[i].c; j--){
			dp[j]=max(dp[j], dp[j-p[i].c]+p[i].a-j*p[i].d);
			ans=max(ans, dp[j]);
		}
	}
	cout << ans << endl;
	return 0;
}





猜你喜欢

转载自blog.csdn.net/sirius_han/article/details/80182475