#10128. 「一本通 4.3 练习 2」花神游历各国
作者:互联网
#10128. 「一本通 4.3 练习 2」花神游历各国(题目链接)
大意:区间开根号,询问区间和
laz 标记区间是否全为 0,1
扩展 % 运算是最坏为 n/2的
#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e5+500;
#define ll long long
#define ls rt<<1,l,mid
#define rs rt<<1|1,mid+1,r
ll tre[maxn<<2],laz[maxn<<2];
int n,m;
ll mp[maxn];
void build(int rt,int l,int r){
laz[rt] = 0;
if(l==r){
tre[rt] = mp[l];
if(tre[rt]==1||tre[rt]==0) laz[rt]=1;
return ;
}
int mid = l+r>>1;
build(ls);build(rs);
tre[rt]=tre[rt<<1]+tre[rt<<1|1];
if(laz[rt<<1]&&laz[rt<<1|1]) laz[rt]=1;
}
ll qur(int rt,int l,int r,int a,int b){
if(l>=a&&r<=b) return tre[rt];
int mid = l+r>>1;
ll an=0;
if(a<=mid) an+=qur(ls,a,b);
if(b>mid) an+=qur(rs,a,b);
return an;
}
void upda(int rt,int l,int r,int a,int b){
if(laz[rt]==1)return ;
if(l==r){
tre[rt] = (ll)sqrt(tre[rt]);
if(tre[rt]==1||tre[rt]==0) laz[rt]=1;
return ;
}
int mid = l+r>>1;
if(a<=mid) upda(ls,a,b);
if(b>mid) upda(rs,a,b);
tre[rt]=tre[rt<<1]+tre[rt<<1|1];
if(laz[rt<<1]&&laz[rt<<1|1]) laz[rt]=1;//0 1都不用再开
}
int main(){
scanf("%d",&n);
for(int i=1;i<=n;++i) scanf("%lld",&mp[i]);
build(1,1,n);
scanf("%d",&m);
int a,b,c;
for(int i=0;i<m;++i){
scanf("%d%d%d",&a,&b,&c);
if(b>c) swap(b,c);
if(a-1){
upda(1,1,n,b,c);
}
else{
printf("%lld\n",qur(1,1,n,b,c));
}
}
return 0;
}
标签:rt,return,4.3,rs,int,ll,tre,花神,10128 来源: https://blog.csdn.net/kumu28/article/details/89052663