CF1840D的題解

Jerry_heng發表於2024-03-28

(一)

比賽結束前 \(5\) 分鐘才調出來。

二分答案。先排序,然後從左往右搜,看是否能在 \(3\) 次以內處理完。

由於是絕對值,控制左右數之差 \(\le\) 選定的數 \(x\)

每次固定左節點 \(l\),搜右節點 \(r\),越遠越好。

搜完後 \(l=r+1\),繼續搜。

特判 \(n\le3\) 的情況。

(二)

AC 程式碼。

#include<bits/stdc++.h>
#define int long long
using namespace std;
int t,n,a[200001],sum;
int up(int x){
	if(x&1)return x/2+1;
	else return x/2;
}
bool check(int x){
	int l=1,r=1;
	int cnt=0;
	while(++cnt){
		if(cnt==4)return 0;
		while(r<n&&a[r+1]<=a[l]+2*x)r++;
		if(r==n)break;
		l=r+1,r++;
	}
	return 1;
}
signed main(){
	scanf("%lld",&t);
	while(t--){
		scanf("%lld",&n);
		for(int i=1;i<=n;i++)scanf("%lld",&a[i]);
		if(n<=3){
			puts("0");
			continue;
		}
		sort(a+1,a+n+1);
		int l=0,r=up(a[n]-a[1]),ans;
		while(l<=r){
			int mid=(l+r)>>1;
			if(check(mid))ans=mid,r=mid-1;
			else l=mid+1;
		}
		printf("%lld\n",ans);
	}
	return 0;
}