0%

CF-1019-C. Median Splits

思路讲解

首先,注意到,这道题目我们是不在意这个段的中位数到底是几的,我们只在意这个段的中位数是 >K>K还是 K≤K 。因此我们只需要通过记录 K≤K 的数的数量,就可以知道符不符合要求。

那么前缀和后缀可以用这种方法比较简便的求得,那么中间的怎么办呢?

以前缀为例,在处理的时候,直接判断该位置和最近的前缀合法位置能不能组合为两个合法段。(贪心地,我们认为总是和最近的段组合为两个合法段)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
vector<ll> pres;
FOR(i,1,N){
preA[i]=preA[i-1];
if(A[i]<=K){
++preA[i];
}
if(!pres.empty()){
// 将这个点和之前合法的前缀组合一下,看看呢能不能凑出两个合法段
ll len=i-pres.back();
ll num=preA[i]-preA[pres.back()];
if(num>=ceil(len/2.0)){
cout<<"YES\n";
return;
}
}
if(preA[i]>=ceil(i/2.0l)){
pres.pb(i);
}
}

AC代码

https://codeforces.com/contest/2103/submission/318394685

心路历程(WA,TLE,MLE……)