自用线段树模板

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了自用线段树模板相关的知识,希望对你有一定的参考价值。

已经没什么好说的了。

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #define maxn 100010
 5 using namespace std;
 6 long long a[maxn];
 7 struct segment_tree{
 8     long long sum[maxn<<2+1];long long add[maxn<<2+1];
 9     #define lson o<<1
10     #define rson o<<1|1
11     inline void push_down(int o,int l,int r){
12         if(!add[o]) 
13             return;
14         add[lson] += add[o];
15         add[rson] += add[o];
16         int mid = (l+r) >> 1;
17         sum[lson] += add[o]*(mid - l + 1);
18         sum[rson] += add[o]*(r - mid);
19         add[o] = 0;
20     }
21     inline void push_up(int o){ 
22         sum[o] = sum[lson] + sum[rson];
23     }
24     inline void build(int o,int l,int r){
25         add[o] = 0; 
26         if(l == r){
27             sum[o] = a[l];
28             return;
29         }
30         int mid = (l+r) >> 1;
31         build(lson,l,mid);
32         build(rson,mid+1,r);
33         push_up(o);
34     }
35     inline long long calc_sum(int o,int l,int r,int ql,int qr){
36         if(ql <= l && qr >= r) 
37             return sum[o];
38         int mid = (l+r) >> 1;
39         push_down(o,l,r);
40         long long ans = 0;
41         if(ql <= mid) 
42             ans += calc_sum(lson,l,mid,ql,qr);
43         if(qr > mid) 
44             ans += calc_sum(rson,mid+1,r,ql,qr);
45         return ans;
46     }
47     inline void update(int o,int l,int r,int ql,int qr,int v){
48         if(ql <= l && qr >= r){
49             add[o] += v;
50             sum[o] += v*(r - l + 1);
51             return;
52         }
53         int mid = (l+r) >> 1;
54         push_down(o,l,r);
55         if(ql <= mid) 
56             update(lson,l,mid,ql,qr,v);
57         if(qr > mid) 
58             update(rson,mid+1,r,ql,qr,v);
59         push_down(o,l,r);
60         push_up(o);
61     }
62 };
63 int n,m;
64 segment_tree tree;
65 inline int read(){
66     int num = 0;
67     char c;
68     bool flag = false;
69     while ((c = getchar()) ==   || c == \n || c == \r);
70     if (c == -)
71         flag = true;
72     else
73         num = c - 0;
74     while (isdigit(c = getchar()))
75         num = num * 10 + c - 0;
76     return (flag ? -1 : 1) * num;
77 } 
78 int main(){
79     n = read();m = read();
80     for(int i=1;i<=n;i++) 
81       a[i] = 1ll*read();
82     tree.build(1,1,n);
83     for(int i=1;i<=m;i++){
84         int opt,x,y;
85         long long k;
86         opt = read();
87         if(opt == 2){
88             x = read();y = read();
89             long long int s = tree.calc_sum(1,1,n,x,y);
90             printf("%lld\n",s);
91         }
92         if(opt == 1){
93             x = read();y = read();k = read();
94             tree.update(1,1,n,x,y,k);
95         }
96     }
97     return 0;
98 }

 

以上是关于自用线段树模板的主要内容,如果未能解决你的问题,请参考以下文章

自用最小生成树模板(基于Kruskal)

[自用]模板坑待填

洛谷P3372线段树模板1——线段树

线段树模板 (poj 3468)

线段树模板整理

线段树模板总结