5937. 斩杀计划

Description
        众所周知,小J和小G是死对头,一天小G带领一群小弟找到了小J。
问题描述
        小G有n个小弟,第i个小弟有ai点攻击力,小G有m点血量。
        小J在小G找小第的时间里去找小Z学到了膜法,他在大战前配置了三种魔法药水
        1:复用型药水:花费1法力值,选择小G的攻击力小于等于2的一个小弟让他跟随自己(变为自己的小弟并且攻击力和属于小G时一样)
        2:猎人药水:花费4法力值,选择小G的攻击力小于等于3的一个小弟让他跟随自己
        3:腐败药水:花费1法力值,使小G所有小弟攻击力降低三点(使用前两种魔法将小弟拉到自己阵营时小弟攻击力就是当前的攻击力,即小J的小弟攻击力只能为1,2,3)
        为了向小G展现自己的力量,他打算在召集到一些小弟后发动攻击(每个小弟打一次)直接秒杀小G(攻击力大于等于m)
        由于智商有限,小J在配置腐败药水时会花费很大精力,他需要知道自己最少使用多少腐败药水,并在腐败药水数量最小的情况下花费最小的法力值
 
Input
第一行两个正整数n,m表示小G的小弟数量和血量
第二行n个正整数表示小G所有小弟的攻击力
Output
        一行两个整数表示最小的腐败药水数量和在腐败药水最小的情况下法力值花费,如果无论如何都无法战胜,输出一个整数-1
 
Sample Input
Sample Input1:
3 5
1 2 3

Sample Input2:
8 8
10 20 30 40 50 60 70 80

Sample Input3:
8 80
10 20 30 40 50 60 70 80
Sample Output
Sample Output1:
0 5

样例说明
        对2,3小弟使用复用型药水和猎人药水

Sample Output2:
16 23

样例说明
使用16个腐败药水
在第3个腐败药水时拉10,攻击力为1
在第6个腐败药水时拉20,攻击力为2
在第9个腐败药水时拉30,攻击力为3
在第16个腐败药水时拉50,攻击力为2

Sample Output3:
-1
 做法:贪心,显然2>1>3
 1 #include <cstdio>
 2 #include <cstring>
 3 #include <iostream>
 4 #include <algorithm>
 5 #define N 5000007
 6 using namespace std;
 7 int n,m;
 8 int a[N],list[N],tot;
 9 
10 inline int read(){
11     int s=0;
12     char ch=getchar();
13     for(;ch<'0'||ch>'9';ch=getchar());
14     for(;ch>='0'&&ch<='9';s=s*10+ch-'0',ch=getchar());
15     return s;
16 }
17 
18 int main(){
19     freopen("zhanshajihua.in","r",stdin);
20     freopen("zhanshajihua.out","w",stdout);
21     n=read();
22     m=read();
23     for(register int i=1;i<=n;++i) a[i]=read();
24     sort(1+a,1+a+n);
25     if (m==0){
26         printf("0 0");
27         return 0;
28     }
29     register int sum=0,ans=0,attack=0;
30     for(register int i=1;i<=n;){
31         while(a[i]-sum*3>0) ++sum;
32         --sum;
33         int j=i;
34         while(j<=n){
35             if (a[j]-sum*3>3) break;
36             while(a[j]-sum*3==0&&j<=n) j++;
37             if (a[j]-sum*3<3) ++ans,attack+=a[j]-sum*3,list[++tot]=a[j]-sum*3;
38             else ans+=4,attack+=3,list[++tot]=3;
39             ++j;
40         }
41         if (attack>=m) break;
42         i=j; 
43     }
44     ans+=sum;
45     sort(list+1,list+tot+1);
46     while(tot&&list[tot]==3){
47         if (attack-list[tot]>=m){
48             if (list[tot]==3)    attack-=3,ans-=4;
49             else attack-=list[tot],--ans;
50         }
51         if (attack==m) break;
52         tot--;
53     }
54     int j=1;
55     while(j<=tot){
56         if (attack-list[j]>=m){
57             if (list[j]==3)    attack-=3,ans-=4;
58             else attack-=list[j],--ans;
59         }
60         if (attack==m) break;
61         j++;
62     }
63     if (attack>=m) printf("%d %d",sum,ans);
64     else printf("-1");
65 }
View Code

 

转载于:https://www.cnblogs.com/traveller-ly/p/9892465.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值