三分(凸函数)

题目链接:https://www.cometoj.com/contest/33/problem/B

题目大意:一个小区中任意两个房子的高度差必须要小于等于M米。因此房地产商必须要调整房子的高度,使得任意两个房子的高度差均小于等于M米。每个房子只能改变一次高度,将一个房子的高度改变k米的花费是k^2万元,求房地产商最低要花费多少万元。

具体思路:三分这些楼层中可以存在的最小高度。

AC代码:

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 # define ll long long
 4 # define inf 0x3f3f3f3f
 5 const int maxn  = 2e5+100;
 6 ll n,m;
 7 ll a[maxn];
 8 ll cal(ll tmp)
 9 {
10     ll ans=0;
11     for(int i=1; i<=n; i++)
12     {
13         if(a[i]<tmp)
14             ans+=(tmp-a[i])*(tmp-a[i]);
15         else if(a[i]>tmp+m)
16             ans+=(a[i]-tmp-m)*(a[i]-m-tmp);
17     }
18     return ans;
19 }
20 ll solve(ll l,ll r){
21     ll mid,midd;
22     ll ans=0;
23     while(l<r-1)
24     {
25         mid=(l+r)/2ll;
26         midd=(mid+r)/2ll;
27         if(cal(mid)>=cal(midd)){
28             ans=cal(mid);
29             l=mid;
30         }
31         else
32         {
33             ans=cal(midd);
34             r=midd;
35         }
36     }
37     return ans;
38 }
39 int main()
40 {
41     ll minn=inf,maxx=-inf;
42     scanf("%d %d",&n,&m);
43     for(int i=1; i<=n; i++)
44     {
45         scanf("%d",&a[i]);
46         minn=min(minn,a[i]);
47         maxx=max(maxx,a[i]);
48     }
49     printf("%lld\n",solve(minn,maxx));
50 }

 

posted @ 2019-03-21 09:14  Let_Life_Stop  阅读(396)  评论(0编辑  收藏  举报