BFS实现线段树区间加和区间查询,求助时间复杂度
查看原帖
BFS实现线段树区间加和区间查询,求助时间复杂度
649095
幻想繁星NM 猫猫可爱楼主2023/6/17 14:30
#include<bits/stdc++.h>
using namespace std;
int n,m;
long long a[100005];
long long t[500005],lazy[500005];
int L[500005],R[500005];
queue<int>q;
void build(int i,int l,int r)
{
	L[i]=l;R[i]=r;
	if(l==r)
	{
		t[i]=a[l];
		return;
	}
	build(i<<1,l,l+r>>1);
	build(i<<1|1,(l+r>>1)+1,r);
	t[i]=t[i<<1]+t[i<<1|1];
}
void add(int l,int r,int d)
{
	q.push(1);
	int i;
	while(!q.empty())
	{
		i=q.front();
		q.pop();
		if(L[i]>r||R[i]<l)
			continue;
		if(L[i]>=l&&R[i]<=r)
		{
			lazy[i]+=d;
			continue;
		}
		t[i]+=(min(R[i],r)-max(L[i],l)+1)*d;
		q.push(i<<1);
		q.push(i<<1|1);
	}
}
long long ask(int l,int r)
{
	q.push(1);
	int i;
	long long ans=0;
	while(!q.empty())
	{
		i=q.front();
		q.pop();
		if(L[i]>r||R[i]<l)
			continue;
		ans+=(min(R[i],r)-max(L[i],l)+1)*lazy[i];
		if(L[i]>=l&&R[i]<=r)
		{
			ans+=t[i];
			continue;
		}
		q.push(i<<1);
		q.push(i<<1|1);
	}
	return ans;
}
int main()
{
	read(n,m);
	for(int i=1;i<=n;i++)
		a[i]=read();
	build(1,1,n);
	int opt,l,r,d;
	while(m--)
	{
		read(opt,l,r);
		if(opt==1)
		{
			d=read();
			add(l,r,d);
		}
		else
			write(ask(l,r),'\n');
	}
	return 0;
}
2023/6/17 14:30
加载中...