二分线段树求调60pts
查看原帖
二分线段树求调60pts
550325
hdbhdbhdb楼主2024/10/21 17:30
#include<bits/stdc++.h>
#define int long long
using namespace std;
struct init{
	int l,r,sum,lazy;
}t[800010];
int n,q,w,a[200010];
void push_down(int x){
	t[2*x].lazy+=t[x].lazy;
	t[2*x].sum+=t[x].lazy*(t[2*x].r-t[2*x].l+1);
	t[2*x+1].lazy+=t[x].lazy;
	t[2*x+1].sum+=t[x].lazy*(t[2*x+1].r-t[2*x+1].l+1);
	t[x].lazy=0;
}
void push_up(int x){
	t[x].sum=t[x<<1].sum+t[x<<1|1].sum;
}
void intt(int l,int r,int x){
	t[x].l=l,t[x].r=r;
	t[x].lazy=0;
	
	if(l==r){
		t[x].sum=a[l];
		return;
	}
	int mid=(l+r)>>1;
	intt(l,mid,x<<1);
	intt(mid+1,r,x<<1|1);
	push_up(x);
}
void ad(int x,int l,int r,int d){
	if(t[x].l>=l&&t[x].r<=r){
		t[x].lazy+=d;
		t[x].sum+=(t[x].r-t[x].l+1)*d;
		return;
	}
	push_down(x);
	int mid=(t[x].r+t[x].l)>>1;
	if(l<=mid) ad(x<<1,l,r,d);
	if(r>mid) ad(x<<1|1,l,r,d);
	push_up(x);
}
int query(int l,int r,int x){
	int res=0;
	if(l<=t[x].l&&t[x].r<=r) return t[x].sum;
	int mid=(t[x].l+t[x].r)>>1;
	push_down(x);
	if(l<=mid) res+=query(l,r,x<<1);
	if(r>mid) res+=query(l,r,x<<1|1);
	return res;
}
int er(int l,int r,int k,int c){
	int mid=(l+r)>>1,q1=c*query(1,mid,1);
	if(q1==k) return mid-1;
	if(l==r) return l-1;
	if(q1>k) return er(l,mid,k,c);
	return er(mid+1,r,k,c);
}
signed main(){
//	freopen("wxyt.in","r",stdin);
//	freopen("wxyt.out","w",stdout);
	cin>>n>>q>>w;
	for(int i=1;i<=n;i++){
		scanf("%lld",&a[i]);
	}
	intt(1,n,1);
	while(q--){
		int L,R,D;
		scanf("%lld%lld%lld",&L,&R,&D);
		ad(1,L,R,D);
		int h=query(1,n,1),ans=0,ww=w,c=1;
		while(ww-h*c>0){
			ans+=n;
			ww-=h*c;
			c=c<<1;
		}
		ans+=er(1,n,ww,c);
		printf("%lld\n",ans);
	}
	return 0;
}//9 1 4 5 1 4
2024/10/21 17:30
加载中...