我们发现,$\operatorname{mi}$ 反而更大了,若现在让 $i+1$,得:
$\operatorname{maxn}=10,\operatorname{minn}=2, \operatorname{mi}=\operatorname{maxn}-\operatorname{minn}=10-2=8$。
我们发现,$\operatorname{mi}$ 变小了,答案更优了,说明每次更新最小值的指针即可。
::::success[证明]
- 若更新最小值,$\operatorname{mi}$ 显然会变小。
- 若更新最大值,$\operatorname{mi}$ 显然会变大。
- 若更新中间值,$\operatorname{mi}$ 显然不变,没有任何效果。
故,更新最小值最优。
::::
例如:
```cpp
if (a[i] == minn) ++i;
else if (b[j] == minn) ++j;
else if (c[k] == minn) ++k;
else ++l;
```
最后,输出 $\operatorname{mi}$ 即可。
最后梳理:
- 排序:将四个班级的身高数组分别排序。
- 四指针扫描:使用四个指针分别指向四个数组的当前位置。
- 贪心策略:每次移动当前最小值所在的指针。
- 更新答案:记录过程中的最小差值。
## 代码:
```cpp
#include<bits/stdc++.h>
using namespace std;
#define int long long
const int N = 75010;
int n, a[N], b[N], c[N], d[N], mi = 1e9;
signed main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
cin >> n;
int i;
for (i = 1; i <= n; i++) cin >> a[i];
for (i = 1; i <= n; i++) cin >> b[i];
for (i = 1; i <= n; i++) cin >> c[i];
for (i = 1; i <= n; i++) cin >> d[i];
sort(a + 1, a + 1 + n);
sort(b + 1, b + 1 + n);
sort(c + 1, c + 1 + n);
sort(d + 1, d + 1 + n);
i = 1;
int j = 1, k = 1, l = 1;
while (i <= n && j <= n && k <= n && l <= n) {
int maxn = max({a[i], b[j], c[k], d[l]});
int minn = min({a[i], b[j], c[k], d[l]});
mi = min(mi, maxn - minn);
if (a[i] == minn) ++i;
else if (b[j] == minn) ++j;
else if (c[k] == minn) ++k;
else ++l;
}
cout << mi;
CODE BY no_coding_extra
return 0;
}
```