您的位置:首页 > 其它

(ssl 1377)竞赛真理

2017-12-16 07:31 218 查看
DescriptionTENSHI在经历了无数次学科竞赛的失败以后,得到了一个真理:做一题就要对一题!但是要完全正确地做对一题是要花很多时间(包括调试时间),而竞赛的时间有限。所以开始做题之前最好先认真审题,估计一下每一题如果要完全正确地做出来所需要的时间,然后选择一些有把握的题目先做。 当然,如果做完了预先选择的题目之后还有时间,但是这些时间又不足以完全解决一道题目,应该把其他的题目用贪心之类的算法随便做做,争取“骗”一点分数。
任 务 :根据每一题解题时间的估计值,确定一种做题方案(即哪些题目认真做,哪些题目
     “骗”分,哪些不做),使能在限定的时间内获得最高的得分,
Input
第一行有两个正整数N和T,表示题目的总数以及竞赛的时限(单位秒)。以下的N行,每行4个正整数W1i 、T1i 、W2i 、T2i ,分别表示第i题:完全正确做出来的得分,完全正确做出来所花费的时间(单位秒),“骗”来的分数,“骗”分所花费的时间(单位秒)。
其中,3 ≤ N ≤ 30,2 ≤ T ≤ 1080000,1 ≤ W1i 、W2i ≤ 30000,1 ≤ T1i 、T2i ≤ T。
Output
所能得到的最高分值Sample Input
样例1
4 10800
18 3600 3 1800
22 4000 12 3000
28 6000 0 3000
32 8000 24 6000

样例2
3 7200
50 5400 10 900
50 7200 10 900
50 5400 10 900
Sample Output
样例1
50

样例2
70
第一种方法:分组背包
动态规划算法
#include <cstdio>
#include <algorithm>
using namespace std;
int w[61],c[61],v,n,t,a[61][3],f[1080001];
int main(){
scanf("%d%d",&n,&v); n=n*2;
for (int i=1;i<=n;i++){
scanf("%d%d",&c[i],&w[i]);
a[(i-1)/2+1][++a[(i-1)/2+1][0]]=i; //n种冲突。
}
for (int k=1;k<=n/2;k++)
for (int j=v;j>=min(w[k*2-1],w[k*2]);j--) //01背包
for (int i=1;i<=2;i++)
if (j>=w[a[k][i]]){
int tmp=a[k][i];
if (f[j]<f[j-w[tmp]]+c[tmp]) f[j]=f[j-w[tmp]]+c[tmp]; //最大值
}
printf("%d",f[v]); return 0;
}

首先:动态规划肯定会时间很长:(时间复杂度:O(NV)=30*1080000≈3*10^7)空间复杂度会更糟。
所以因为n不大,就用深搜(时间复杂度O(2^n)(当然要剪枝))
#include <cstdio>
using namespace std;
double p[50];
int ans,n,m,v[50],q[50],h[50],g[50];
void tru(int dep,int s,int t){
if (dep>n){
if (s>ans) ans=s; //找到方案
return;
}
if (t*p[dep]+s<ans) return; //剪枝
tru(dep+1,s,t);
if (v[dep]<=t) tru(dep+1,s+q[dep],t-v[dep]); //能搜就搜
if (h[dep]<=t) tru(dep+1,s+g[dep],t-h[dep]); //能搜就搜
}
void sort(){
int i,j,t; double x;
for (i=1;i<=n-1;i++)
for (j=i+1;j<=n;j++)
if (p[i]<p[j]){
x=p[i];p[i]=p[j];p[j]=x;
t=q[i];q[i]=q[j];q[j]=t;
t=v[i];v[i]=v[j];v[j]=t;
t=g[i];g[i]=g[j];g[j]=t;
t=h[i];h[i]=h[j];h[j]=t;
}
}
int main(){
double x;
scanf("%d%d",&n,&m);
for (int i=1;i<=n;i++){
scanf("%d%d%d%d",&q[i],&v[i],&g[i],&h[i]);
p[i]=(double)q[i]*1.0/v[i];  x=(double)g[i]*1.0/h[i]; //比值!!
if (x>p[i]) p[i]=x;
}
sort(); //排序
tru(1,0,m); //深搜
printf("%d",ans);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: