zoukankan      html  css  js  c++  java
  • 1281 山峰和旗子

    用一个长度为N的整数数组A,描述山峰和山谷的高度。山峰需要满足如下条件, 0 < P < N - 1 且 A[P - 1] < A[P] > A[P + 1]。
     
     
    现在要在山峰上插上K个旗子,并且每个旗子之间的距离 >= K,问最多能插上多少个旗子(即求K的最大值)。两个山峰之间的距离为|P - Q|。
    以上图为例,高度为:1 5 3 4 3 4 1 2 3 4 6 2。其中可以作为山峰的点为:1 3 5 10。
     
    放2面旗子, 可以放在1 和 5。
    放3面旗子, 可以放在1 5 和 10。
    放4面旗子, 可以放在1 5 和 10,之后就放不下了。
    所以最多可以放3面旗子。
    Input
    第1行:一个数N,表示数组的长度(1 <= N <= 50000)。
    第2 - N + 1行:每行1个数Ai(1 <= Ai <= 10^9)。
    Output
    输出最多能插上多少面旗子(即求K的最大值)。
    Input示例
    12
    1 
    5 
    3 
    4 
    3 
    4 
    1 
    2 
    3 
    4 
    6 
    2
    Output示例
    3

    思路:2分,找到可以插旗子的点,然后二分旗子个数,看是否满足有这么多个
     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 
     4 int a[50004];
     5 int b[50004];
     6 int s=0;
     7 
     8 int slove(int x){
     9     int sum=0,ssum=0;
    10     for(int i=2;i<=s;i++){
    11         sum+=b[i]-b[i-1];
    12        // cout<<i<<" "<<sum<<endl;
    13         if(sum>=x){
    14             ssum++;sum=0;
    15         }
    16     }
    17   //  cout<<endl;
    18     return ssum+1;
    19 }
    20 int main(){
    21     int n;
    22     scanf("%d",&n);
    23     for(int i=1;i<=n;i++){
    24         scanf("%d",&a[i]);
    25     }
    26 
    27     for(int i=2;i<n;i++){
    28         if(a[i]>a[i-1]&&a[i]>a[i+1]){
    29             b[++s]=i;
    30         }
    31     }
    32     int l=1,r=s,mid;
    33     int ans=0;
    34     while(l<=r){
    35         int mid=(l+r)>>1;
    36         //cout<<mid<<" "<<slove(mid)<<endl;
    37         if(slove(mid)>=mid){
    38             ans=mid;
    39             l=mid+1;
    40         }
    41         else r=mid-1;
    42     }
    43     cout<<ans<<endl;
    44 }
  • 相关阅读:
    团队项目-选题报告
    图论3-分层图最短路
    图论2-次短路计数
    图论1-k短路
    noi online 提高组t2冒泡排序
    图和树
    搜索(bfs)
    搜索(dfs)
    笔记
    打工
  • 原文地址:https://www.cnblogs.com/hhxj/p/7087194.html
Copyright © 2011-2022 走看看