首先感谢抱抱熊dalao的题解,提供了一种比较简单的思路。
[抱抱熊dalao的题解](https://note.youdao.com/ynoteshare1/index.html?id=52f087d1427e209252c30d79c0be98fd&type=note)
[题目链接](http://acm.zzuli.edu.cn/problem.php?id=2558)
简单的说每次最小值+1都会让这个值已经这个数左边的元素处于这个数左边的元素和这个数右边的元素直接,所以我们就枚举出最大的左边元素,然后除以元素数量。至于为什么要向下取整,是因为如果有小数,则左边这组数的最小值与“左边元素相差1”,这时候向下取整就是最小的元素。最大值同理向上取整。
#include<cstdio> #include<stack> #include<queue> #include<cmath> #include<climits> #include<cstring> #include<cstdlib> #include<cctype> #include<algorithm> #include<iostream> #include<string> #include<vector> #define INF 233333333333333 using namespace std; typedef long long ll; typedef pair<int, int> P; const int maxn = 100005; int num[maxn]; int main(void) { int T; cin >> T; while(T--) { int n, k; cin >> n >> k; for (int i = 0; i<n; i++) scanf("%d", &num[i]); sort(num, num+n); double sum1 = k, sum2 = -k; int c1 = 0, c2 = 0; for (int i = 0; i<n; i++) { //计算数组最小值能达到最大值时左边元素的累加值 if (sum1 + num[i] < num[i] * (i+1)) break; sum1 += num[i], c1++; } for (int j = n-1; j>= 0; j--) { //计算数组最大值能达到的最小值时右边元素的累加值 if (sum2 + num[j] > num[j] * (n-j)) break; sum2 += num[j], c2++; } cout << max(0, (int)(ceil(sum2/c2) - floor(sum1/c1) + 1e-10)) << endl; //计算最小值的最大值并向下取整&&计算最大值的最小值并向上取整,如果最小值大于最大值 //则说明数组能达到最小值与最大值相等的状态 } return 0; }