标签:ons const signed lower guess sig view ble fine
比较厉害的一个题目吧
我们首先发现 \(M=min(M,A+R)\)
然后考虑二分做这个题
二分高度,考虑怎么 \(check\)
我们发现这个题对于一个已知的高度,怎么求花费呢?
把多于和少于高度 \(H\) 的砖的数目统计出来,然后这个数乘上 \(M\) 再加上缺少的乘 \(A\) 或者是多出来的乘 \(R\)
这么统计答案,随着给定 \(H\) 的增加,答案是个单谷的(可以手推一下……)
这个波谷在 \(\frac {sum} 2\) 或者 \(\frac{sum} 2+1\) 中
但是不要忘记把每个砖的高都作为最终高度算一下(防卡)
所以可能就不需要二分了
别忘了先 \(sort\)
复杂度:\(O(n\log n)\)
(居然复杂度又到了 \(sort\) 上)
#include<bits/stdc++.h>
using namespace std;
#define int long long
namespace yspm{
inline int read()
{
int res=0,f=1; char k;
while(!isdigit(k=getchar())) if(k==‘-‘) f=-1;
while(isdigit(k)) res=res*10+k-‘0‘,k=getchar();
return res*f;
}
const int N=1e5+10;
int n,a,r,m,h[N],sum[N],ans=1e15+10;
inline int solve(int x)
{
int pos=lower_bound(h+1,h+n+1,x)-h-1,res=0;
int c1=x*pos-sum[pos],c2=sum[n]-sum[pos]-x*(n-pos);
res=min(c1,c2); c1-=res; c2-=res; res*=m;
res+=c1*a+c2*r;
return res;
}
signed main()
{
n=read(); a=read(); r=read(); m=read();
m=min(m,a+r);
for(int i=1;i<=n;++i) h[i]=read();
sort(h+1,h+n+1);
for(int i=1;i<=n;++i) sum[i]=sum[i-1]+h[i];
ans=min(solve(sum[n]/n+1),solve(sum[n]/n));
for(int i=1;i<=n;++i) ans=min(ans,solve(h[i]));
printf("%lld\n",ans);
return 0;
}
}
signed main(){return yspm::main();}
记得 \(dp\) 碰壁的时候想想贡献二分啥的
Codeforces1355E Guess Divisors Count
标签:ons const signed lower guess sig view ble fine
原文地址:https://www.cnblogs.com/yspm/p/12942767.html