线段树二分35pts求救(悬赏一个关注,有hack数据)
查看原帖
线段树二分35pts求救(悬赏一个关注,有hack数据)
534689
dubnium楼主2023/9/26 09:57

码风良好,变量名清晰,随时在线(在线等,急)

#include<bits/stdc++.h>
#define LL long long
#define int long long
using namespace std;
const LL maxn=2e5+6,INF=-(0x3f3f3f3f);
struct Segment_tree {
	int l,r;
	LL cnt0,sum,lmax,rmax,dat,tag;
} T[maxn<<3];
int n,m;
void spread(int p) {
	if(T[p].tag) {
		T[p<<1].sum=(T[p<<1].r-T[p<<1].l+1)*T[p].tag;
		T[p<<1|1].sum=(T[p<<1|1].r-T[p<<1|1].l+1)*T[p].tag;

		T[p<<1].lmax=max(T[p].tag,(T[p<<1].r-T[p<<1].l+1)*T[p].tag);
		T[p<<1|1].lmax=max(T[p].tag,(T[p<<1|1].r-T[p<<1|1].l+1)*T[p].tag);

		T[p<<1].rmax=max(T[p].tag,(T[p<<1].r-T[p<<1].l+1)*T[p].tag);
		T[p<<1|1].rmax=max(T[p].tag,(T[p<<1|1].r-T[p<<1|1].l+1)*T[p].tag);

		T[p<<1].dat=max(T[p].tag,(T[p<<1].r-T[p<<1].l+1)*T[p].tag);
		T[p<<1|1].dat=max(T[p].tag,(T[p<<1|1].r-T[p<<1|1].l+1)*T[p].tag);

		T[p<<1].cnt0=(T[p].tag==INF?0:1)*(T[p<<1].r-T[p<<1].l+1);
		T[p<<1|1].cnt0=(T[p].tag==INF?0:1)*(T[p<<1|1].r-T[p<<1|1].l+1);

		T[p<<1].tag=T[p<<1|1].tag=T[p].tag,T[p].tag=0;
	}
	return ;
}
void pushup(int p) {
	T[p].sum=T[p<<1].sum+T[p<<1|1].sum;
	T[p].lmax=max(T[p<<1].lmax,T[p<<1].sum+T[p<<1|1].lmax);
	T[p].rmax=max(T[p<<1|1].rmax,T[p<<1|1].sum+T[p<<1].rmax);
	T[p].dat=max({T[p<<1].dat,T[p<<1|1].dat,T[p<<1].rmax+T[p<<1|1].lmax});
	T[p].cnt0=T[p<<1].cnt0+T[p<<1|1].cnt0;
	//printf("%lld %lld %lldg\n",p,T[p<<1].cnt0,T[p<<1|1].cnt0);
}
void Build(int p,int l,int r) {
	T[p].l=l,T[p].r=r;
	if(l==r) {
		T[p].dat=T[p].lmax=T[p].rmax=T[p].sum=INF,T[p].cnt0=T[p].tag=0;
		return ;
	}
	int mid=l+r>>1;
	Build(p<<1,l,mid),Build(p<<1|1,mid+1,r);
	pushup(p);
}
void change(int p,int x,int y,int v) {
	if(x<=T[p].l&&T[p].r<=y) {
		//printf("%lld %lld %lldh\n",p,T[p].l,T[p].r);
		T[p].sum=v*(T[p].r-T[p].l+1);
		T[p].lmax=max(v,v*(T[p].r-T[p].l+1));
		T[p].rmax=max(v,v*(T[p].r-T[p].l+1));
		T[p].dat=max(v,v*(T[p].r-T[p].l+1));
		T[p].cnt0=(v==INF?0:1)*(T[p].r-T[p].l+1);
		//printf("%lld %lld %lldj\n",p,T[p].cnt0,T[p].dat);
		T[p].tag=v;
		return ;
	}
	spread(p);
	int mid=T[p].l+T[p].r>>1;
	if(x<=mid)
		change(p<<1,x,y,v);
	if(y>mid)
		change(p<<1|1,x,y,v);
	pushup(p);
}
Segment_tree query(int p,int x,int y) {
	if(x>y) return {0,0,0,0,0,0,0,0};
//	cout<<p<<' '<<x<<' '<<y<<" "<<T[p].l<<' '<<T[p].r<<endl;
	if(x<=T[p].l&&T[p].r<=y)
		return T[p];
	spread(p);
	int mid=T[p].l+T[p].r>>1;
	Segment_tree res,a,b;
	if(y<=mid)
		return query(p<<1,x,y);
	if(x>mid)
		return query(p<<1|1,x,y);
	a=query(p<<1,x,y),b=query(p<<1|1,x,y);
	res.sum=a.sum+b.sum;
	res.lmax=max(a.lmax,a.sum+b.lmax);
	res.rmax=max(b.rmax,b.sum+a.rmax);
	res.dat=max({a.dat,b.dat,a.rmax+b.lmax});
	res.cnt0=a.cnt0+b.cnt0;
	return res;
}
int Find(int p,LL v) {
	if(T[p].l==T[p].r) {
		return T[p].cnt0<v?-1:T[p].l;
	}
	spread(p);
	if(T[p<<1].cnt0>=v)
		return Find(p<<1,v);
	return Find(p<<1|1,v-T[p<<1].cnt0);
}
void debug(int u)
{
	spread(u);
	if (T[u].l == T[u].r) {
		//printf("%llddebug\n", T[u].r - T[u].l + 1 - T[u].cnt0);
		return;
	}
	debug(u << 1), debug(u << 1 | 1);
}
signed main() {
	scanf("%lld%lld",&n,&m);
	Build(1,1,n);
	int opt,l1,r1,l2,r2;
	while(m--) {
		scanf("%lld%lld%lld",&opt,&l1,&r1);
		if(!opt){
//			puts("before");
//			debug(1);
			change(1,l1,r1,1);
//			puts("after");
//			debug(1);
		}
		else if(opt==1) {
			scanf("%lld%lld",&l2,&r2);
			//if(l1==l2&&r1==r2)continue;
//			puts("before");
//			debug(1);
			int cnt1 = (r1-l1+1)-query(1,l1,r1).cnt0;
			change(1, l1, r1, 1);
			int cnt0 = query(1,1,l2-1).cnt0;
			int t=Find(1,cnt1 + cnt0);
			if (cnt1 == 0) continue;
			if(t==-1) change(1,l2,r2,INF);
			else change(1,l2,t,INF);
//			puts("after");
//			debug(1);
//			cout<<"sdf"<<cnt0<<' '<<cnt1<<endl;
			//	printf("%df\n",t);
		} else
			printf("%lld\n",max(0ll, query(1,l1,r1).dat));
		//printf("%lld %lld %lld %lldk\n",query(1,1,1).cnt0,query(1,2,2).cnt0,query(1,3,3).cnt0,query(1,4,4).cnt0);
	}
	return 0;
}
/*
4 8
1 3 3 1 4
1 3 4 2 2
0 3 3
1 2 4 2 4
2 2 3
0 2 2
1 1 4 1 4
0 1 1
*/

hack数据: 4 8 1 3 3 1 4 1 3 4 2 2 0 3 3 1 2 4 2 4 2 2 3 0 2 2 1 1 4 1 4 0 1 1 答案:1

2023/9/26 09:57
加载中...