zoukankan      html  css  js  c++  java
  • [树状数组]模板

    【模板】树状数组

    题目描述

    如题,已知一个数列,你需要进行下面两种操作:

    1.将某一个数加上x

    2.求出某区间每一个数的和

    输入

    输入格式:

    第一行包含两个整数N、M,分别表示该数列数字的个数和操作的总个数。

    第二行包含N个用空格分隔的整数,其中第i个数字表示数列第i项的初始值。

    接下来M行每行包含3或4个整数,表示一个操作,具体如下:

    操作1: 格式:1 x k 含义:将第x个数加上k

    操作2: 格式:2 x y 含义:输出区间[x,y]内每个数的和

    输出

    输出格式:

    输出包含若干行整数,即为所有操作2的结果。

    样例输入

    5 5
    1 5 4 2 3
    1 1 3
    2 2 5
    1 3 -1
    1 4 2
    2 1 4

    样例输出

    14
    16

    提示

    对于30%的数据:N<=8,M<=10


    对于70%的数据:N<=10000,M<=10000


    对于100%的数据:N<=500000,M<=500000

     
    代码:
     1 #include<cstdio>
     2 const int Maxv = 500005; 
     3 
     4 int sum[Maxv], n; 
     5 
     6 int lowbit(int x) {
     7     return x & (-x); 
     8 }
     9 
    10 int getsum(int x) {
    11     int ans = 0;
    12     for (int i = x; i > 0; i -= lowbit(i)) {
    13         ans += sum[i];
    14     }
    15     return ans;
    16 }
    17 
    18 void add(int x, int y) {
    19     for (int i = x; i <= n; i += lowbit(i)) {
    20          sum[i] += y; 
    21     }
    22     return; 
    23 }
    24 
    25 int main() {
    26     int m; 
    27     scanf("%d%d", &n, &m); 
    28     for (int i = 1; i <= n; i++) {
    29         int tmp; 
    30         scanf("%d", &tmp); 
    31         add(i, tmp); 
    32     }
    33     while(m--) {
    34         int t, x, y; 
    35         scanf("%d%d%d", &t, &x, &y); 
    36         if (t == 1) {
    37             add(x, y); 
    38         }
    39         else {
    40             printf("%d
    ", getsum(y) - getsum(x - 1)); 
    41         }
    42     }
    43     return 0; 
    44 }
     
  • 相关阅读:
    js日期时间补零
    判断交换机性能好坏的九个因素
    [转]document.getElementById("...") is null
    ABAP数据库操作之操作语句Insert
    abap对excel处理
    选择屏幕搜索帮助
    Screen返回选择界面的问题
    ABAP 的TABLE CONTROL实践积累
    ALV的双击使用
    双击ALV调用事务代码并传入参数
  • 原文地址:https://www.cnblogs.com/GldHkkowo/p/8847937.html
Copyright © 2011-2022 走看看