Cod sursa(job #1322292)

Utilizator retrogradLucian Bicsi retrograd Data 19 ianuarie 2015 22:18:29
Problema Arbori indexati binar Scor 40
Compilator cpp Status done
Runda Arhiva educationala Marime 1.72 kb
#include<fstream>
#include<vector>
#include<cmath>
#define NMAX 50000

using namespace std;

ifstream fin("aib.in");
ofstream fout("aib.out");

long A[NMAX], TREE[15*NMAX];
int n, Q;

void makeTree(int node, int cs, int cd) {
    if(cs == cd) {
        TREE[node] = A[cs];
    } else {
        makeTree(node*2, cs, (cs+cd)/2);
        makeTree(node*2+1, (cs+cd)/2+1, cd);
        TREE[node] = TREE[node*2]+TREE[node*2+1];
    }
}

void addTo (int poz, long val, int node, int cs, int cd) {
    TREE[node] += val;
    if(cs==cd) return;
    int mid = (cs+cd)/2;
    if(poz<=mid)
        addTo(poz, val, node*2, cs, mid);
    else
        addTo(poz, val, node*2+1, mid+1, cd);
}

long getSum (int l, int r, int node, int cs, int cd) {
    if(l>cd || r<cs) return 0;
    if(l<=cs && r>=cd) return TREE[node];
    else {
        int mid = (cs+cd)/2;
        return getSum (l, r, node*2, cs, mid) +
               getSum (l, r, node*2+1, mid+1, cd);
    }
}

int firstK (long val, int node, int cs, int cd) {
    while(TREE[node] > val) {
        node*=2; cd=(cd+cs)/2;
    }
    long sum = TREE[node];
    while(sum<val) {
        cd++;
        sum+=A[cd];
    }
    return ((sum == val)?cd:-1);

}

int main() {
    fin>>n>>Q;

    for(int i=1; i<=n; i++) {
        fin>>A[i];
    }

    makeTree(1, 1, n);

    int type, a, b;
    for(int i=1; i<=Q; i++) {
        fin>>type;
        if(type == 0) {
            fin>>a>>b;
            A[a] += b;
            addTo(a, b, 1, 1, n);
        } else if(type == 1) {
            fin>>a>>b;
            fout<<getSum(a, b, 1, 1, n)<<'\n';
        } else {
            fin>>a;
            fout<<firstK(a, 1, 1, n)<<'\n';
        }
    }
}