• Welcome to the world's largest Chinese hacker forum

    Welcome to the world's largest Chinese hacker forum, our forum registration is open! You can now register for technical communication with us, this is a free and open to the world of the BBS, we founded the purpose for the study of network security, please don't release business of black/grey, or on the BBS posts, to seek help hacker if violations, we will permanently frozen your IP and account, thank you for your cooperation. Hacker attack and defense cracking or network Security

    business please click here: Creation Security  From CNHACKTEAM

LibreOJ 131树状数组2:区间修改,单点查询


Recommended Posts

题目地址

Solution

前面已经知道了树状数组的单点修改和区间查询。这里利用差分的思想:具体来说,维护\(b\)数组:

\[b=a-a[i-1]

\]

其中\(a\)为原来数组。可以发现

\sum_{k=1}^ib[k

\]

因此我们只需要对\(b\)利用树状数组维护,get_sum即可得到原来数组单点的值。而对于区间更新,我们只需要在两个端点\(l,r\)打上标记即可:

\[update(l,x);更新(r 1,-x)

\]

点击查看代码

int n,q;

const int N=1e 6 5;

ll a[N],b[N];

ll c[N];

ll低位(int x){ return x(-x);}

void update(int i,ll k){

//在第我个位置添加k

while(i=N){

c=ll(k);I=低位(I);

}

}

ll get_sum(int i){

//从1-我中获取总和

ll ans=0;

while(i0){

ans=ll(c);I-=低位(I);

}

返回美国国家标准(American National Standards的缩写)

}

int main(){

//IOs : sync _ with _ stdio(false);

n=read();q=read();

for(int I=1;I=n;i ){

scanf('%lld ',a);

b=a-a[I-1];

update(i,b);

}

while(q - ){

int tmp=read();

if(tmp==1){

int l=read(),r=read();

ll x;scanf('%lld ',x);

update(l,x);update(r 1,-x);

}

否则{

int pos=read();

cout get _ sum(pos)endl;

}

}

}

Link to comment
Share on other sites