zoukankan      html  css  js  c++  java
  • 【BZOJ 2151】 2151: 种树 (贪心+堆+双向链表)

    2151: 种树

    Description

    A城市有一个巨大的圆形广场,为了绿化环境和净化空气,市政府决定沿圆形广场外圈种一圈树。园林部门得到指令后,初步规划出n个种树的位置,顺时针编号1到n。并且每个位置都有一个美观度Ai,如果在这里种树就可以得到这Ai的美观度。但由于A城市土壤肥力欠佳,两棵树决不能种在相邻的位置(i号位置和i+1号位置叫相邻位置。值得注意的是1号和n号也算相邻位置!)。最终市政府给园林部门提供了m棵树苗并要求全部种上,请你帮忙设计种树方案使得美观度总和最大。如果无法将m棵树苗全部种上,给出无解信息。

    Input

    输入的第一行包含两个正整数n、m。第二行n个整数Ai。

    Output

    输出一个整数,表示最佳植树方案可以得到的美观度。如果无解输出“Error!”,不包含引号。

    Sample Input

    【样例输入1】
    7 3
    1 2 3 4 5 6 7
    【样例输入2】
    7 4
    1 2 3 4 5 6 7

    Sample Output

    【样例输出1】
    15

    【样例输出2】
    Error!
    【数据规模】
    对于全部数据:m<=n;
    -1000<=Ai<=1000
    N的大小对于不同数据有所不同:
    数据编号 N的大小 数据编号 N的大小
    1 30 11 200
    2 35 12 2007
    3 40 13 2008
    4 45 14 2009
    5 50 15 2010
    6 55 16 2011
    7 60 17 2012
    8 65 18 199999
    9 200 19 199999
    10 200 20 200000

    HINT

    Source

    【分析】

      应该是一种很经典的贪心吧【为什么我不会。。。

      贪心思想:每次选择合法的最大的一个

      如果这是这样当然是错的,要给他一点后悔的机会【感觉有点网络流的思想啊

      假设你选的最大的一个是x2,x1、x3和他相邻,其实可能你的最优方案是不选x2,而选x1、x3【但是一定两个都选,不可能只选x1或x3,因为x2最大

      所以我们把x1 x2 x3 都删掉,插入一个新结点,贡献为x1+x3-x2,如果选了他,说明你反悔了,决定选x1、x3而放弃x2。

      【思路就是这么巧妙简单啊~~

     1 #include<cstdio>
     2 #include<cstdlib>
     3 #include<cstring>
     4 #include<iostream>
     5 #include<algorithm>
     6 #include<cmath>
     7 #include<queue>
     8 #include<vector>
     9 using namespace std;
    10 #define Maxn 200010
    11 
    12 struct node
    13 {
    14     int x,id;
    15     friend bool operator < (node x,node y)
    16     {
    17         return x.x<y.x;
    18     }
    19 };
    20 
    21 priority_queue<node > q;
    22 
    23 bool mark[2*Maxn];
    24 int lt[2*Maxn],nt[2*Maxn],w[2*Maxn];
    25 
    26 int main()
    27 {
    28     int n,m;
    29     scanf("%d%d",&n,&m);
    30     for(int i=0;i<n;i++) scanf("%d",&w[i]);
    31     
    32     if(m>n/2) printf("Error!
    ");
    33     else
    34     {
    35         int ans=0,cnt=n-1;
    36         while(!q.empty()) q.pop();
    37         for(int i=0;i<n;i++)
    38         {
    39             node nw;
    40             nw.x=w[i];nw.id=i;
    41             q.push(nw);
    42         }
    43         for(int i=0;i<n;i++) nt[i]=(i+1)%n;
    44         for(int i=0;i<n;i++) lt[i]=(i-1+n)%n;
    45         memset(mark,0,sizeof(mark));
    46         for(int i=1;i<=m;i++)
    47         {
    48             while(mark[q.top().id]) q.pop();
    49             node nw=q.top();q.pop();
    50             ans+=nw.x;
    51             cnt++;
    52             mark[lt[nw.id]]=mark[nt[nw.id]]=1;
    53             nt[lt[lt[nw.id]]]=cnt;lt[nt[nt[nw.id]]]=cnt;
    54             nt[cnt]=nt[nt[nw.id]];lt[cnt]=lt[lt[nw.id]];
    55             node xx;
    56             w[cnt]=w[lt[nw.id]]+w[nt[nw.id]]-nw.x;
    57             xx.x=w[cnt];xx.id=cnt;
    58             q.push(xx);
    59         }
    60         printf("%d
    ",ans);
    61     }
    62     return 0;
    63 }
    View Code

    2017-01-13 20:32:36

  • 相关阅读:
    杭电oj2032、2040、2042、2054、2055
    杭电oj2022-2030
    杭电oj2012-2021
    杭电oj2000-2011
    值得思考的几句话,放在这看看
    CEO 是一家创业公司的天花板
    致敬骄傲的产品人
    【新业务搭建】竞争情报业务规划及体系构建的思考——By Team
    微软威胁情报中心总经理的十句话——From John Lambert——太精辟了.......
    【调研与分析】标杆学习、知识管理和竞争情报的关系——From Team
  • 原文地址:https://www.cnblogs.com/Konjakmoyu/p/6284056.html
Copyright © 2011-2022 走看看