线段树模板

1.

    单点更新(add),区间查询

   

void update(int p,int add,int rt,int l,int r)  

{  

    if(p>r) return;  

    if(l==r)  

    {  

        tree[rt].sum+=add;  

        return;  

    }  

    else  

    {  

        int m=(l+r)>>1;  

        if(p<=m) update(p,add,lson);//3. 要p的作用哪。只更新一半 。因为下面有Pushup  

        else update(p,add,rson);  

    }  

    Pushup(rt);  

}  

int query(int a,int b,int rt,int l,int r)  

{  

    int ans=0;  

    if(a<=l&&b>=r)  

    {  

        return tree[rt].sum;  

    }  

    else  

    {  

        int m=(l+r)>>1;  

        if(a<=m)  

            ans+=query(a,b,lson);  

        if(b>m) //4. 这地方是r>m果断而不是r>=m  

            ans+=query(a,b,rson);  

    }  

    return ans;  

}  


2.

     单点更新,区间最值查询

     与1的主要区别就是Max的更新吧。  

void Pushup(int rt)

{

    tree[rt].Max=max(tree[rt<<1].Max,tree[rt<<1|1].Max);

}



void build(int rt,int l,int r)

{

   if(l==r) {scanf("%d",&tree[rt].Max);return;}//1. 这地方一开始忘了return

   else

   {

       int m=(l+r)>>1;

       build(lson);

       build(rson);

   }

   Pushup(rt);

}

void update(int a,int b,int rt,int l,int r)

{

    if(l==r) {tree[rt].Max=b;return;}

    else

    {

        int m=(l+r)>>1;

        if(a<=m) update(a,b,lson);

        if(a>m)  update(a,b,rson);

    }

    Pushup(rt);

}

int query(int a,int b,int rt,int l,int r)

{

    int ans=0;

    if(a<=l&&b>=r) //2. 这地方不留意错写成l==r  return 还是自己不理解。

    {

        return tree[rt].Max;

    }

    else

    {

        int m=(l+r)>>1;

        if(a<=m) ans=max(ans,query(a,b,lson));

        if(b>m) ans=max(ans,query(a,b,rson));

    }

    return ans;

}

 

 

 

 

你可能感兴趣的:(线段树)