Poj2018 Best Cow Fences
Farmer John's farm consists of a long row of N (1 <= N <= 100,000)fields. Each field contains
a certain number of cows, 1 <= ncows <= 2000.
FJ wants to build a fence around a contiguous group of these fields in order to maximize the
average number of cows per field within that block. The block must contain at least F (1 <= F <= N)
fields, where F given as input.
Calculate the fence placement that maximizes the average, given the constraint.
输入N个数,从中取至少F个数,这些数的平均值越大越好!
输入
* Line 1: Two space-separated integers, N and F.
* Lines 2..N+1: Each line contains a single integer, the number of cows in a field.
Line 2 gives the number of cows in field 1,line 3 gives the number in field 2, and so on.
输出
* Line 1: A single integer that is 1000 times the maximal average.Do not perform rounding, just print the integer that is 1000*ncows/nfields.
样例输入
10 6
6
4
2
10
3
8
5
9
4
1
样例输出
6500
//先二分平均数,然后将各个元素减去平均数,处理前缀和。 //然后利用前缀和,判断最大子段和是否大于0。 #include<cstdio> #include<algorithm> using namespace std; int n,m;double b[100001],a[100001],sum[100001]; int main() { scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) scanf("%lf",&a[i]); double l=0,r=2000,minn=1e-5; while(r-l>minn) { double mid=(l+r)/2,maxx=1e10,ans=-1e10;//二分平均数 for(int i=1;i<=n;i++) b[i]=a[i]-mid,sum[i]=b[i]+sum[i-1];//将每块地的牛的头数都减去平均数,再求前缀和 for(int i=m;i<=n;i++)//计算m~n块地的最大字串和 { maxx=min(maxx,sum[i-m]);//在sum[0]~sum[i-m]中选最小值 ans=max(ans,sum[i]-maxx);//所有sum[i]-maxx中取最大,即最大子段和 } if(ans>=0) l=mid;//如果ans>=0,则说明能够到达平均数,平均数还可以再提高 else r=mid;//否则说明不能到达,平均数应降低 } printf("%d",(int)(r*1000));//题目要求答案*1000 }