zoukankan      html  css  js  c++  java
  • 学姐出的毒奶题之yjj

    【写在前面】——在调试了n遍代码之后,终于自己给自己解了毒,也终于可以开始更新我的第一篇博文

    【再说几句】——OpenSnow巨佬的影响力非常广泛,在她的带动下,我也决定改题!哈哈哈~,但由于我比较懒,就不粘原题了,直接改喽。

    【开始正经】

    <题目背景>

    众所周知,可爱的乔治是一位能吃的小猪,他经常会把看好的吃的加进自己的购物车里面。而他还小,没有多少零花钱,不舍得吃特别贵的事物。

    <题目描述>

    就在这时,乔治的姐姐佩奇想要帮助乔治。如果帮乔治买一次事物(即购物车食物的非空子集),佩奇可以得到这次购买食物的最大价值的钱(佩奇也是为了赚点零花钱),而要花费的代价是这次所购买的食物价值的平均值。

    乔治因为有了佩奇的帮助,变的越来越贪婪(事实上可爱的乔治才不会这样,都怪这个毒奶的题目),所以每次往购物车里加的东西都会不比购物车中的任何物品价值低。

    佩奇想要得到最多的钱,请问她购买一次事物能得到的最大价值是多少(即佩奇当前可以赚的最多零花钱是多少)?

    <输入输出格式>

    输入格式

    第一行有一个整数n,表示操作次数。

    第1~n+1行,每行有一个操作类型:如果为1,则还有一个数k,表示乔治这次加入购物车的食物的价值;如果为2,表示佩奇想知道当前的最大收益。

    输出格式

    对于每一个2操作,输出1行1个4位浮点数,表示当前的最大收益。答案四舍五入。

    输入输出样例

    数据范围

    对于5%的数据,保证和样例一模一样

    对于30%的数据,保证n<=2000

    对于100%的数据,保证n<=500000

    【先粘代码】

    #include<cstdio>
    #include<algorithm>
    #include<cmath>
    #include<iostream>
    #include<cstring>
    using namespace std;
    struct node
    {
        int a,k;
    }t[50005];
    int main()
    {
        //freopen("yjj.in","r",stdin);
        //freopen("yjj.out","w",stdout);
        int n;
        double ave,wei,sum = 2,li; //因为每次都先算好两个食物的平均数,因此sum一开始就为2
        scanf("%d",&n);
        for(int i = 2;i <= n + 1;i++)
        {
      scanf("%d",&t[i - 1].a);
      if(t[i - 1].a == 1) scanf("%d",&t[i - 1].k);
     }
        for(int i = 1;i <= n;i++)
     {
      if(t[i].a == 1) continue;//如果是1操作,则继续
      else if(t[i].a == 2)//如果是2操作
      {
        wei = t[1].k + t[i - 1].k;//先算出第一个食物和这个2操作之前内个食物的总价
        ave = wei / sum;//求出两个食物的平均价格
        for(int j = 2;j < i - 1;j++)//从第二个食物开始枚举,枚举到倒数第二个食物
        {
          if(t[j].a == 1 && t[j].k < ave)//如果枚举的当前食物的价格比之前所求的平均值小
          {
            wei += t[j].k;//就买它
            sum++;//食物总数累加1
            ave = wei / sum;//求出当前平均值,为下一次比较做准备
          }
        }
          li = t[i - 1].k - ave;//佩奇的收益
          printf("%.4lf ",li);

      }
      return 0;
    }

    【胡乱分析】

    瑞拉我(对,就是我)做这道题的时候,没有注意到“非空子集”这四个字,导致佩奇把所有食物都买了,然后求收益。这样导致样例1过了样例2就过不了,于是各种改double、int,然后样例2过了样例1又过不了。。。后来经学姐的指点,和被自己的毒气快要击毙的时候,写对了代码。。。

    那么这道题怎么做呢?首先,关注的点不应该是四舍五入(它好像会自己四舍五入),而是非空子集上,佩奇并不是傻到把所有食物都买,所以这是一道贪心题。读入数据完毕后,先不着急算,开始进入一个循环,直到遇到2操作,然后把第一个食物和最后一个食物的价值加起来,再取平均值,因为这两个食物肯定是要选的(一个最大,一个最小),接下来从第2个食物开始枚举,一直到倒数第二个食物,其中,如果枚举到的食物的价值比当前平均值小的话,就买了它,这样它会拉低平均值(就像你拉低班级平均分。。额开个玩笑),这样佩奇花的钱就少了,如果比当前平均值大,当然是不买了。这道题的思路就是这样。

    【orz】

    如果哪个地方写错了,或者emmmm,还请大佬尽情鄙视我,要是能回复就更好了。(或者有没有更简短的代码啥的)

    【呕对这个代码好像二十个点只过了一个点,大佬救救我】

  • 相关阅读:
    CVE-2017-10271
    [GKCTF2020]cve版签到
    [GXYCTF2019]禁止套娃 无参数RCE
    [护网杯 2018]easy_tornado
    记两道xctf上的web进阶区 反序列化
    msf卸载win defender
    Cron表达式详解
    Linux ifconfig只有lo没有别的网络的问题
    记一道文件上传
    【解决】手机安卓已经导入burp证书,但仍提示此证书并非来自被信任的机构
  • 原文地址:https://www.cnblogs.com/peppa/p/8463402.html
Copyright © 2011-2022 走看看