https://www.cometoj.com/contest/33/problem/B?problem_id=1456
此题思路很简单因为房屋高度差不能超过m,所以先假设最低高度不低于h,那么最高的高度就小于h+m。因此只需要枚举i从1到2e5。而花费就是cost = (h-b1)^2 + ...+ (h-bn)^2 = h*n - 2*h*(b1+...+bn) + (b1^2+...+bn^2)
然后给出代码
#include <iostream>
#include <algorithm>
#include <climits>
using namespace std;
int n,m;
long long h[200005];
long long b[200005],c[200005];
long long res = LLONG_MAX;
int main() {
cin >> n >> m;
for(int i=0; i<n; i++) {
cin >> h[i];
}
sort(h,h+n);
b[0] = h[0];
c[0] = h[0]*h[0];
//int maxh = h[0];
for(int i=1; i<n; i++) {
b[i] = h[i] + b[i-1];
c[i] = h[i] * h[i] + c[i-1];
}
for(int i=1; i<200001; i++) {
// cout << "i = " << i << endl;
long long cost = 0;
long long pos_min = upper_bound(h, h+n, i) - h;
long long pos_max = upper_bound(h, h+n, i+m) - h;
cost += pos_min*i*i - 2*b[pos_min-1]*i + c[pos_min-1];
//if (cost <0)
//cout << i << " " << pos_min*i*i << endl;
cost += (n-pos_max)*(i+m)*(i+m) - 2*(b[n-1] - b[pos_max-1])*(i+m) + (c[n-1] - c[pos_max-1]);
//cout << b[n - 1] - b[pos_max-1] << endl;
// if (cost <0)
// cout << i << " " << pos_max << endl;
res = min(res,cost);
}
cout << res;
}
注意:此处有个坑点在于计算cost的时候用i*i*k和k*i*i得到的结果是不同的,两个i先乘不会发生类型转换因此可能越界得到负数。