1. 程式人生 > >洛谷P1873 砍樹

洛谷P1873 砍樹

題目描述

伐木工人米爾科需要砍倒M米長的木材。這是一個對米爾科來說很容易的工作,因為他有一個漂亮的新伐木機,可以像野火一樣砍倒森林。不過,米爾科只被允許砍倒單行樹木。

米爾科的伐木機工作過程如下:米爾科設定一個高度引數H(米),伐木機升起一個巨大的鋸片到高度H,並鋸掉所有的樹比H高的部分(當然,樹木不高於H米的部分保持不變)。米爾科就行到樹木被鋸下的部分。

例如,如果一行樹的高度分別為20,15,10和17,米爾科把鋸片升到15米的高度,切割後樹木剩下的高度將是15,15,10和15,而米爾科將從第1棵樹得到5米,從第4棵樹得到2米,共得到7米木材。

米爾科非常關注生態保護,所以他不會砍掉過多的木材。這正是他為什麼儘可能高地設定伐木機鋸片的原因。幫助米爾科找到伐木機鋸片的最大的整數高度H,使得他能得到木材至少為M米。換句話說,如果再升高1米,則他將得不到M米木材。

輸入輸出格式

輸入格式:
第1行:2個整數N和M,N表示樹木的數量(1<=N<=1000000),M表示需要的木材總長度(1<=M<=2000000000)

第2行:N個整數表示每棵樹的高度,值均不超過1000000000。所有木材長度之和大於M,因此必有解。

輸出格式:
第1行:1個整數,表示砍樹的最高高度。

輸入輸出樣例

輸入樣例#1: 複製
5 20
4 42 40 26 46
輸出樣例#1: 複製
36

#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<queue> #include<algorithm> #include<bits/stdc++.h> #define N 1000009 using namespace std; long long l; long long r; long long n,m; long long a[N]; int main() { scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) { scanf("%d",&a[i]); r=max(r,a[i]); } while
(l<=r) { int mid=(l+r)>>1; long long ans=0; for(int i=1;i<=n;i++) if(a[i]>mid)ans+=a[i]-mid; if(ans<m)r=mid-1; else l=mid+1; } printf("%d",l-1); }
#include<bits/stdc++.h>
long long a[1000009];
long long n,m;
long long sum;
long long ans;
using namespace std;
int main()
 {
    scanf("%lld%lld",&n,&m);
    for(int i=1;i<=n;i++)
     scanf("%lld",&a[i]);
    sort(a+1,a+1+n);
    int i=n;
    while(sum<m)
     {
        sum+=(a[i]-a[i-1])*(n-i+1);
        i--;
       }  
    i++;
    ans=a[i-1]+(sum-m)/(n-i+1);
    printf("%lld",ans);   

 }