Acwing 242.一个简单的的整数问题 —— 差分树状数组(简单版)

题目链接:https://www.acwing.com/problem/content/248/

 1 #include <iostream>
 2 #include <algorithm>
 3 #include <cstring>
 4 #include <cstdio>
 5 
 6 using namespace std;
 7 
 8 typedef long long LL;
 9 const int N = 1e5 + 10;
10 int a[N];
11 LL tr[N];
12 int n, m;
13 
14 int lowbit(int x)
15 {
16     return x & -x;
17 }
18 
19 void add(int x, int k)
20 {
21     for (int i = x; i <= n; i += lowbit(i)) tr[i] += k;
22 }
23 
24 LL sum(int x)
25 {
26     LL res = 0;
27     for (int i = x; i ; i -= lowbit(i)) res += tr[i];
28     return res;
29 }
30 
31 int main()
32 {
33     scanf("%d%d", &n, &m);
34 
35     for (int i = 1; i <= n; i ++ ) scanf("%d", &a[i]);
36 
37     for (int i = 1; i <= n; i ++ ) add(i, a[i] - a[i - 1]);
38 
39     while (m -- )
40     {
41         char op[2]; int l, r, k;
42         scanf("%s%d", op, &l);
43         
44         if (*op == 'C')
45         {
46             scanf("%d%d", &r, &k);
47             add(l, k), add(r + 1, -k);
48         }
49         else 
50         {
51             printf("%lld\n", sum(l));
52         }
53     }
54 
55     return 0;
56 }

此题将前缀和线段树改为了差分树状数组,即每个点存的是a[i] - a[i - 1]。

由此我们可知道,若

树状数组存储的是差分,那sum得到的是修改后数组中的一个值;

树状数组存储的是原数组,那sum得到的是修改后数组的前缀和。

posted @ 2020-12-29 18:15  筱翼深凉  阅读(131)  评论(0)    收藏  举报