前置芝士
线段树基本框架
区间求和
const int N=100010;
ll a[N],st[N*4],f[N*4];
int n,q;
//向上传
void pushup(ll u){
st[u]=st[lc]+st[rc];
}
//向下传
void pushdown(ll u,ll l,ll r,ll mid){
if(f[u]){
st[lc]+=f[u]*(mid-l+1);
st[rc]+=f[u]*(r-mid);
f[lc]+=f[u];
f[rc]+=f[u];
f[u]=0;
}
}
//初始化
void build(ll u,ll l,ll r){
if(l==r){
st[u]=a[l];
return;
}
ll mid=l+r>>1;
build(lc,l,mid);
build(rc,mid+1,r);
pushup(u);
}
//区间更新
void update(ll u,ll l,ll r,ll x,ll y,ll k){
if(x>r||y<l) return;
if(x<=l&&y>=r){
st[u]+=(r-l+1)*k;
f[u]+=k;
return;
}
ll mid=l+r>>1;
pushdown(u,l,r,mid);
update(lc,l,mid,x,y,k);
update(rc,mid+1,r,x,y,k);
pushup(u);
}
//区间查询
ll query(ll u,ll l,ll r,ll x,ll y){
if(x>r||y<l) return 0;
if(x<=l&&r<=y) return st[u];
ll mid=l+r>>1;
pushdown(u,l,r,mid);
return query(lc,l,mid,x,y)+query(rc,mid+1,r,x,y);
}
//build(1,1,n);
//update(1,1,n,l,r,k);
//query(1,1,n,l,r);
区间最值
[python]
class Tree():
def __init__(self):
self.l=0
self.r=0
self.lazy=0
self.val=0
tree=[Tree() for i in range(10*4)]
def build(p,l,r):
if l>r:
return
tree[p].l, tree[p].r, tree[p].lazy, tree[p].val = l, r, 0, 0
if l<r:
mid=(l+r)>>1
build(p<<1,l,mid)
build(p<<1|1,mid+1,r)
def pushUp(p):
tree[p].val=max(tree[p<<1].val,tree[p<<1|1].val)
#单点修改,添加值
def add(p,i,v):
if tree[p].l==tree[p].r:
tree[p].val+=v
else:
mid=(tree[p].l+tree[p].r)>>1
if i>mid:
add(p<<1|1,i,v)
else:
add(p<<1,i,v)
pushUp(p)
def pushdown(p):
if tree[p].lazy:
lazy=tree[p].lazy
tree[p<<1].lazy+=lazy
tree[p<<1|1].lazy+=lazy
tree[p<<1].val+=lazy
tree[p<<1|1].val+=lazy
tree[p].lazy=0
def update(p,l,r, v):
if l<=tree[p].l and r>=tree[p].r:
tree[p].lazy+=v
tree[p].val+=v
return
if r<tree[p].l or l>tree[p].r:
return
if tree[p].lazy:
pushdown(p)
update(p<<1,l,r,v)
update(p<<1|1,l,r,v)
pushUp(p)
def query(p,l,r):
if l<=tree[p].l and r>=tree[p].r:
return tree[p].val
if tree[p].l>r or tree[p].r<l:
return 0
if tree[p].lazy:
pushdown(p)
return max(query(p<<1,l,r),max(p<<1|1,l,r))
build(1,1,10)
update(1,1,5,1)
update(1,7,10,1)
update(1,2,8,1)
update(1,3,4,1)
update(1,9,10,1)
print(query(1,1,10))
[java]
class SegTree{
static final int INF=0x3f3f3f3f;
final int n;
final int[] min,lazy;
SegTree(int n) {
this.n=n;
min=new int[n<<2];
lazy=new int[n<<2];
Arrays.fill(min,INF);
Arrays.fill(lazy,INF);
}
void build(int[] a){
build(1,0,n-1,a);
}
void build(int p,int l,int r,int[] a){
// if(l>r) return;
if(l==r){
min[p]=a[l];
return;
}
int mid=(l+r)>>1;
build(p<<1,l,mid,a);
build(p<<1|1,mid+1,r,a);
min[p]=Math.min(min[p<<1],min[p<<1|1]);
}
void update(int i,int j,int val){
if(i>j) return;
update(i,j,val,0,n-1,1);
}
void update(int i,int j,int val,int st,int ed,int p){
if(i<=st && j>=ed){
min[p]=Math.min(min[p],val);
lazy[p]=Math.min(lazy[p],val);
return;
}
pushDown(p);
int mid=(st+ed)>>1;
if(i<=mid) update(i,j,val,st,mid,p<<1);
if(j>mid) update(i,j,val,mid+1,ed,p<<1|1);
pushUp(p);
}
int query(int i){
return query(0,i,0,n-1,1);
}
int query(int i,int j){
return query(i,j,0,n-1,1);
}
int query(int i,int j,int st,int ed,int p){
if(i<=st && j>=ed){
return min[p];
}
pushDown(p);
int ans=INF;
int mid=(st+ed)>>1;
if(i<=mid) ans=Math.min(ans,query(i,j,st,mid,p<<1));
if(j>mid) ans=Math.min(ans,query(i,j,mid+1,ed,p<<1|1));
return ans;
}
void pushUp(int p){
min[p]=Math.min(min[p<<1],min[p<<1|1]);
}
void pushDown(int p){
if(lazy[p]==INF) return;
min[p<<1]=Math.min(min[p<<1],lazy[p]);
min[p<<1|1]=Math.min(min[p<<1|1],lazy[p]);
lazy[p<<1]=Math.min(lazy[p<<1],lazy[p]);
lazy[p<<1|1]=Math.min(lazy[p<<1|1],lazy[p]);
lazy[p]=INF;
}
}
标签:学习指南,return,int,线段,tree,mid,st,高阶,ll
From: https://www.cnblogs.com/taotao123456/p/17763657.html