1 条题解
-
0
显然一只蚂蚁与一块方糖匹配,是类似图匹配的结构。那么考虑考虑朝距离 的所有方糖连一条边,这个二分图的最大匹配就是答案。
分别记 为位置 的蚂蚁数和方糖数。
运用 Hall 定理,我们知道二分图最大匹配是 $\sum a_i-\max\limits_{S}\{0,\sum_{i \in S}a_i-\sum_{i \in N(S)}b_i\}$。
考虑将 表示为 个不交区间的并 。
则 $N(S)=\big[l_1-L,r_1+L\big]\cup \big[l_2-L,r_2+L\big]\cup\cdots\cup\big[l_k-L,r_k+L\big]$。
这些区间也最好不交,这要求了 。
如果出现了 ,我们可以将区间 合并为区间 ,这样 不变,但 不减。一定是不劣的。
考虑用一个简单的形式刻画 ,可以写成所有区间减去相邻区间交。两个部分的表示都不难,修改后的变化容易表示。
可以直接上线段树转移,维护 表示目前区间左端点选/不选,右端点选/不选的最大值。转移时枚举一下中点怎么选就好了。
需要对坐标离散化一下。时间复杂度 ,空间复杂度 。
#include<bits/stdc++.h> #define vector basic_string #define int long long #define rd read() #define gc pa == pb && (pb = (pa = buf) + fread(buf, 1, 100000, stdin), pa == pb) ? EOF : *pa++ using namespace std; static char buf[100000], * pa(buf), * pb(buf); inline int read(){ register int x=0,s=gc;while(!isdigit(s))s=gc; while(isdigit(s))x=(x<<1)+(x<<3)+(s^48),s=gc; return x; } const int N=500005,inf=1e16; int n,q,L; struct query{ int op,x,v; }t[N]; vector<int> v; struct seg{ int f[N<<2][2][2],w[N<<2],t[N<<2]; inline void chkmax(int &x,int y){ x=x<y?y:x; } inline void pushup(int id){ for(int i:{0,1})for(int j:{0,1})f[id][i][j]=-inf; for(int l1:{0,1})for(int r1:{0,1}) for(int l2:{0,1})for(int r2:{0,1}) chkmax(f[id][l1][r2], f[id<<1][l1][r1]+f[id<<1|1][l2][r2]+(r1&&l2)*w[id]);} inline void push(int id,int k){ t[id]+=k,w[id]+=k; for(int i:{0,1})for(int j:{0,1})f[id][i][j]-=k; chkmax(f[id][0][0],0); } inline void pushdown(int id){ if(t[id])push(id<<1,t[id]),push(id<<1|1,t[id]),t[id]=0; } inline void U(int id,int l,int r,int x,int k){ if(l==r)return f[id][1][1]+=k,void(); int mid=l+r>>1;pushdown(id); x<=mid?U(id<<1,l,mid,x,k):U(id<<1|1,mid+1,r,x,k),pushup(id); } inline void U(int id,int l,int r,int x,int y,int k){ if(x>y)return;if(x<=l&&y>=r)return push(id,k); int mid=l+r>>1;pushdown(id); if(x<=mid)U(id<<1,l,mid,x,y,k); if(y>mid)U(id<<1|1,mid+1,r,x,y,k); if(x<=mid&&y>mid)w[id]+=k;pushup(id); } inline int res(){ return max({f[1][0][0],f[1][0][1],f[1][1][0],f[1][1][1]}); } }T; signed main(){ q=rd,L=rd;for(int i=1;i<=q;++i)t[i]={rd,rd,rd},v+=t[i].x; sort(v.begin(),v.end()),v.erase(unique(v.begin(),v.end()),v.end()),n=v.size(); for(int i=1,l,r,ans=0;i<=q;++i){ if(t[i].op==1) l=lower_bound(v.begin(),v.end(),t[i].x)-v.begin()+1, T.U(1,1,n,l,t[i].v),ans+=t[i].v; else l=lower_bound(v.begin(),v.end(),t[i].x-L)-v.begin()+1, r=upper_bound(v.begin(),v.end(),t[i].x+L)-v.begin(), T.U(1,1,n,l,r,t[i].v); cout<<ans-T.res()<<'\n'; } return 0; }
- 1
信息
- ID
- 7224
- 时间
- 4000ms
- 内存
- 1024MiB
- 难度
- 10
- 标签
- 递交数
- 1
- 已通过
- 1
- 上传者