我有一个疑惑
查看原帖
我有一个疑惑
1044870
Lyrith_with_xQ楼主2023/8/21 17:14

不吸氧是AC,但是为什么我吸氧了后反而全TLE了?
不吸氧 吸氧
确保用的都是相同的一段代码:

提交使用的代码如下:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;

ll tree[2000005],a[500005],n,m,op,l,r,x,lz_tag[2000005];

ll ls(ll n){return n*2;}//计算左子树的下标 
ll rs(ll n){return n*2+1;}//计算右子树的下标 

void pushup(ll n){tree[n]=tree[ls(n)]+tree[rs(n)];}//从下向上传递区间值 
void build(ll n,ll nl,ll nr)//建树,n为节点编号,n所指代的区间为[nl,nr] 
{
	if(nl==nr)//如果到了叶节点 
	{
		tree[n]=a[nl];//把tree[n]赋值为a[nl](因为此时nl==nr而tree[n]=a[nl,nr]区间的加和,所以tree[n]=a[nl]) 
		return;
	}
	ll mid=(nl+nr)/2;//分治法 
	build(ls(n),nl,mid);//递归左子树 
	build(rs(n),mid+1,nr);//递归右子树 
	pushup(n);//更新值 
}

void addtag(ll n,ll nl,ll nr,ll tg)//给节点n打上lazy-tag,并更新 
{
	lz_tag[n]+=tg;//打上lazy-tag
	tree[n]+=tg*(nr-nl+1);//更新 
}

void pushdown(ll n,ll nl,ll nr)//区间不能覆盖时,把lazy-tag传给子树 
{
	if(lz_tag[n])//如果节点n有被标记 
	{
		ll mid=(nl+nr)/2;
		addtag(ls(n),nl,mid,lz_tag[n]);//tag传给左子树 
		addtag(rs(n),mid+1,nr,lz_tag[n]);//tag传给右子树 
		lz_tag[n]=0;//tag被传走了,将节点n的tag设为0 
	}
}

ll update(ll l,ll r,ll n,ll nl,ll nr,ll x)//区间修改,把a[l,r]内的每一个元素都加x 
{
	if(l<=nl&&nr<=r)//如果节点n所指代的区间a[nl,nr]被区间a[l,r]覆盖到了 
	{
		addtag(n,nl,nr,x);//给节点n打上tag 
		return 0;
	}
	pushdown(n,nl,nr);//不能覆盖的话,就把tag传给子树们 
	ll mid=(nl+nr)/2; 
	if(l<=mid)update(l,r,ls(n),nl,mid,x);//递归左子树 
	if(r>mid)update(l,r,rs(n),mid+1,nr,x);//递归右子树 
	pushup(n);//更新 
}

ll query(ll l,ll r,ll n,ll nl,ll nr)//查询区间a[l,r]内所有元素的和,n为当前结点的编号,所指代的区间为a[nl,nr] 
{
	if(l<=nl&&nr<=r)return tree[n];//如果节点n所指代的区间a[nl,nr]被区间a[l,r]覆盖到了 
	pushdown(n,nl,nr);//不能覆盖的话,就把tag传给子树们 
	ll mid=(nl+nr)/2,res=0;
	if(l<=mid)res+=query(l,r,ls(n),nl,mid);//递归左子树 
	if(r>mid)res+=query(l,r,rs(n),mid+1,nr);//递归右子树 
	return res;//返回区间a[l,r]内所有元素的和
}

int main()
{
	scanf("%lld%lld",&n,&m);
	for(int i=1;i<=n;i++)scanf("%lld",&a[i]);
	build(1,1,n);//建树 
	for(int i=0;i<m;i++)
	{
		scanf("%lld",&op);
		switch(op)
		{
			case 1://区间修改,把a[l,r]内的每一个元素都加x 
			{
				scanf("%lld%lld%lld",&l,&r,&x);
				update(l,r,1,1,n,x);
				break;
			}
			case 2://区间查询,查询区间a[l,r]内所有元素的和 
			{
				scanf("%lld",&l);
				printf("%lld\n",query(l,l,1,1,n));
				break;
			}
		}
	}
    return 0;
}

懒,就用前几天写的线段数模板写了

2023/8/21 17:14
加载中...