线段树模版

来源:互联网 发布:ipad装旧版软件 编辑:程序博客网 时间:2024/05/18 03:56
#include <cstdio>#include <cstring>#include <algorithm>#include <iostream>#include <cmath>#define ls l,mid,rt<<1#define rs mid+1,r,rt<<1|1using namespace std;typedef long long ll;const int N=50007;int sum[N<<2];void up(int rt)//更新{    sum[rt]=sum[rt<<1]+sum[rt<<1|1];}void build(int l,int r,int rt)//建树{    if(l==r)    {        scanf("%d",&sum[rt]);        return ;    }    int mid=(r+l)>>1;    build(ls);    build(rs);    up(rt);}int  query(int l,int r,int rt,int L,int R)//L到R之间求和{    if(l>=L&&r<=R) return sum[rt];    int cnt=0;    int mid=(r+l)>>1;    if(L<=mid) cnt+=query(ls,L,R);//向左找    if(R>mid) cnt+=query(rs,L,R);//向右找    return cnt;}void update(int l,int r,int rt,int x,int p)//x为增加的值,p为加值的地方{    if(l==r)    {        sum[rt]+=x;        return;    }    int mid=(r+l)>>1;    if(p<=mid) update(ls,x,p);    else update(rs,x,p);    up(rt);}int main(){}

有区间更新的模板
lazy[]表示根结点的变化数量

#include <iostream>#include <cstdio>#include <algorithm>#include <cmath>#include <cstring>#include <map>#define ls l,mid,rt<<1#define rs mid+1,r,rt<<1|1typedef long long ll;using namespace std;const int N=100007;int sum[N<<2];int laz[N<<2];int flag;void up(int rt){    sum[rt]=sum[rt<<1]+sum[rt<<1|1];}void build(int l,int r,int rt){    laz[rt]=0;    if(l==r)    {        sum[rt]=0;        return;    }    int mid=(l+r)>>1;    build(ls);    build(rs);    up(rt);}void down(int rt,int len)//len为区间长度{    if(laz[rt])  //如果lazy被标记过那么进行转移    {        sum[rt<<1]+=(len-len/2)*laz[rt];        sum[rt<<1|1]+=(len/2)*laz[rt];        laz[rt<<1]+=laz[rt];        laz[rt<<1|1]+=laz[rt];        laz[rt]=0;    }}void update(int l,int r,int rt,int L,int R){    if(l>=L&&r<=R)    {        sum[rt]+=(r-l+1);//对l-r区间进行操作        laz[rt]++;        return ;    }    down(rt,r-l+1); //对lazy数组进行转移    int mid=(l+r)>>1;    if(L<=mid) update(ls,L,R);    if(R>mid) update(rs,L,R);    up(rt);//当前节点sum值改变,但是它的父节点sum值没有变化,所以用up将当前的值加到父节点}void query(int l,int r,int rt)//查询根结点{    if(l==r)    {        //对根结点进行操作  (操作之前考虑是否有lazy数组未处理)    }    int mid=(l+r)>>1;    down(rt,r-l+1);    query(ls);    query(rs);}int main(){}
原创粉丝点击