CF2157D Billion Players Game
发现最终答案为\(x\times p+y\)的形式,所以当\(a>0\)时\(p=l\)取到最小值否则\(p=r\)取到最小值。
考虑先决定满足\(a_i<l||r<a_i\)的\(a_i\),设此时答案为\(A\times p+B\)。分类讨论
当\(A\le0\)时\(p\)取\(l\)所以要声称一些\(p-a_i\)直到\(A==0(\)或\(a_i\)全部分配完\()\) 发现要取最小的\(-A\)个\(a_i\)。剩下的最大和最小匹配,变成\(\begin{array}{lr}\ \ \ \ a_i-p+p-a_j\\=a_i-a_j\end{array}\) 计算答案
\(A>0\)同理
代码
#include<bits/stdc++.h>
using namespace std;
namespace IO{
template<typename T>
inline void read(T&x){
x=0;char c=getchar();bool f=0;
while(!isdigit(c)) c=='-'?f=1:0,c=getchar();
while(isdigit(c)) x=x*10+c-'0',c=getchar();
f?x=-x:0;
}
template<typename T>
inline void write(T x){
if(x==0){putchar('0');return ;}
x<0?x=-x,putchar('-'):0;short st[50],top=0;
while(x) st[++top]=x%10,x/=10;
while(top) putchar(st[top--]+'0');
}
inline void read(char&c){c=getchar();while(isspace(c)) c=getchar();}
inline void write(char c){putchar(c);}
inline void read(string&s){s.clear();char c;read(c);while(!isspace(c)&&~c) s+=c,c=getchar();}
inline void write(string s){for(int i=0,len=s.size();i<len;i++) putchar(s[i]);}
template<typename T>inline void write(T*x){while(*x) putchar(*(x++));}
template<typename T,typename...T2> inline void read(T&x,T2&...y){read(x),read(y...);}
template<typename T,typename...T2> inline void write(const T x,const T2...y){write(x),putchar(' '),write(y...),sizeof...(y)==1?putchar('\n'):0;}
}using namespace IO;
#define int long long
const int maxn=200010;
int a[maxn];
void solve(){
int n,l,r,p=0,b=0;read(n,l,r);
vector<int>vt;
for(int i=1;i<=n;i++){
read(a[i]);
if(a[i]<l) p++,b-=a[i];
else if(a[i]>r) p--,b+=a[i];
else vt.push_back(a[i]);
}
if(p<0){
sort(vt.begin(),vt.end(),greater<int>());
while(!vt.empty()&&p<0) p++,b-=vt.back(),vt.pop_back();
}
else{
sort(vt.begin(),vt.end());
while(!vt.empty()&&p) p--,b+=vt.back(),vt.pop_back();
}
sort(vt.begin(),vt.end());
for(int i=0;i<vt.size()/2;i++) b+=vt[vt.size()-i-1]-vt[i];
if(p<0) write(r*p+b);
else write(l*p+b);
write('\n');
}
signed main(){
int T;read(T);
while(T--) solve();
return 0;
}

浙公网安备 33010602011771号