zoukankan      html  css  js  c++  java
  • C++线段树模板(区间和、区间加)

    操作说明:

    • segtree<T>tree(len) =>创建一个内部元素类型为T、区间为1~len的线段树tree
    • tree.build(l,r) =>以[l,r]区间建立线段树
    • tree.update(l,r,val,1,len) =>区间[l,r]所有元素加上val
    • tree.query(l,r,1,len) =>计算区间[l,r]的元素和
    #include <iostream>
    #include <string>
    #include <cstdio>
    #include <cmath>
    #include <cstring>
    #include <algorithm>
    #include <vector>
    #include <queue>
    #include <deque>
    #include <map>
    #define range(i,a,b) for(auto i=a;i<=b;++i)
    #define LL long long
    #define itrange(i,a,b) for(auto i=a;i!=b;++i)
    #define rerange(i,a,b) for(auto i=a;i>=b;--i)
    #define fill(arr,tmp) memset(arr,tmp,sizeof(arr))
    using namespace std;
    template <class T>
    class segtree{
    private:
        T* add,*sum;
        void pushup(int rt){
            sum[rt]=sum[rt<<1]+sum[rt<<1|1];
        }
        void pushdown(int rt,int m){
            if(add[rt]){
                add[rt<<1]+=add[rt];
                add[rt<<1|1]+=add[rt];
                sum[rt<<1]+=add[rt]*(m-(m>>1));
                sum[rt<<1|1]+=add[rt]*(m>>1);
                add[rt]=0;
            }
        }
    public:
        explicit segtree(int len=int(1e5+5)){
            add=new T[len<<2];
            sum=new T[len<<2];
            fill(add,0);fill(sum,0);
        }
        void build(int l,int r,int rt=1){
            add[rt]=0;
            if(l==r){
                sum[rt]=0;
                return;
            }
            int m=(l+r)>>1;
            build(l,m,rt<<1);
            build(m+1,r,rt<<1|1);
            pushup(rt);
        }
        void update(int L,int R,T c,int l,int r,int rt=1){
            if(L<=l&&r<=R){
                add[rt]+=c;
                sum[rt]+=c*(r-l+1);
                return;
            }
            pushdown(rt,r-l+1);
            int m=(l+r)>>1;
            if(L<=m)update(L,R,c,l,m,rt<<1);
            if(m<R)update(L,R,c,m+1,r,rt<<1|1);
            pushup(rt);
        }
        T query(int L,int R,int l,int r,int rt=1){
            if(L<=l&&r<=R)return sum[rt];
            pushdown(rt,r-l+1);
            int m=(l+r)>>1;
            T ret=0;
            if(L<=m)ret+=query(L,R,l,m,rt<<1);
            if(m<R)ret+=query(L,R,m+1,r,rt<<1|1);
            return ret;
        }
    };
    int main() {
        segtree<int>tree(10);
        tree.build(1,10);
        tree.update(1,5,1,1,10);
        cout<<tree.query(1,5,1,10)<<endl;
        return 0;
    }
    View Code
  • 相关阅读:
    蓝桥杯java 基础练习 完美的代价
    C# 获得手机归属地功能
    c# HttpWebRequest与HttpWebResponse(转)
    C# Winfrom小黄鸡功能调用
    Winfrom 抓取web页面内容代码
    Winform将网页生成图片
    Winform上传下载文件代码
    Jquery LigerUI框架学习(二)之Tree于Tab标签实现iframe功能
    Jquery LigerUI框架学习(一)
    C# 生成简单验证码
  • 原文地址:https://www.cnblogs.com/Rhythm-/p/9373052.html
Copyright © 2011-2022 走看看