题目描述
体节
贪心,每人每次分给的一定是所需代价最小的 v [ i ] − 1 v[i]-1 v[i]−1个,且分给他的只需要比上一个人多一个。
代码
#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <cstring>
#define ll long long
using namespace std;
const ll INF=1000000000019260817LL;
ll add(ll a,ll b)
{a+=b;return a>=INF?INF:a;}
const int Q=2000005;
ll sm[Q],v[Q],cmp[Q],lazy=0;
int tot=0;
int fa[Q],si[Q],ls[Q],rs[Q],ct[Q];
int rt=0;
void upd(int x)
{
si[x]=si[ls[x]]+si[rs[x]]+ct[x];
sm[x]=add(add(sm[ls[x]],sm[rs[x]]),v[x]);
}
void xxx(int x)
{
int y=fa[x],z=fa[y];
if(ls[z]==y)ls[z]=x;
if(rs[z]==y)rs[z]=x;
if(ls[y]==x)ls[y]=rs[x],rs[x]=y,fa[ls[y]]=y;
else rs[y]=ls[x],ls[x]=y,fa[rs[y]]=y;
fa[x]=z,fa[y]=x;
upd(y),upd(x);
}
void splay(int x)
{
while(fa[x])
{
int y=fa[x],z=fa[y];
if(z)
if((ls[z]==y&&ls[y]==x)||(rs[z]==y&&rs[y]==x))
xxx(y),xxx(x);
else xxx(x),xxx(x);
else xxx(x);
}
rt=x;
}
void INS(ll val,int sz)
{
ll ops=val*sz;
if(!rt)
{
rt=++tot;
v[tot]=sm[tot]=ops;
si[tot]=ct[tot]=sz;
cmp[tot]=val;
return;
}
int p=rt;
while(1)
{
si[p]+=sz;
sm[p]=add(sm[p],ops);
if(val==cmp[p])
{
v[p]=add(v[p],ops);
ct[p]+=sz;
splay(p);
return;
}
if(val<cmp[p])
if(ls[p])p=ls[p];
else{ls[p]=++tot;break;}
else if(rs[p])p=rs[p];
else{rs[p]=++tot;break;}
}
fa[tot]=p;
ct[tot]=si[tot]=sz;
v[tot]=sm[tot]=ops;
cmp[tot]=val;
splay(tot);
}
char buf[1<<20],*p1,*p2;
#define GC (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<20,stdin),p1==p2)?0:*p1++)
inline int R()
{
int t=0;
char o=GC;
while(o>57||o<48)o=GC;
while(o>=48&&o<=57){
t=(t<<1)+(t<<3)+o-48;
o=GC;
}
return t;
}
int main()
{
int n,x;
ll k;
scanf("%d%lld",&n,&k);
for(int i=1;i<=n;i++)
{
++lazy;
x=R();
--x;
if(x<=0)
{
printf("%lld\n",k);
rt=0;
INS(k-lazy,1);
if(i>1)INS(-lazy,i-1);
continue;
}
if(x>si[rt])
{
puts("-1");
--lazy;
INS(-1-lazy,1);
continue;
}
int p=rt,now=x;
while(1)
{
if(si[ls[p]]>=now)p=ls[p];
else if(si[ls[p]]+ct[p]>=now)break;
else now-=si[ls[p]]+ct[p],p=rs[p];
}
splay(p);
ll mus=add(cmp[p]*((ll)x-si[ls[p]]),sm[ls[p]]);
mus=add(mus,(ll)x*lazy);
if(mus>k)
{
puts("-1");
--lazy;
INS(-1-lazy,1);
continue;
}
printf("%lld\n",k-mus);
int ned=i-1-x-si[rs[p]],wil=i-1-x;
rs[p]=0;
if(ned==ct[p])
{
if(!ls[p])rt=0;
else{
int m=ls[p];
while(rs[m])m=rs[m];
splay(m);
rs[m]=0;
upd(m);
}
}
else ct[p]-=ned,v[p]-=cmp[p]*ned,upd(p);
if(wil)INS(-lazy,wil);
INS(k-mus-lazy,1);
}
return 0;
}