Cod sursa(job #3220464)

Utilizator error1000Udrea Dan Mihai error1000 Data 3 aprilie 2024 18:53:16
Problema Arbori indexati binar Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.8 kb
#include <iostream>
#include <fstream>
#include <cassert>

using namespace std;

int N, M;
long long int v[100001];

void add(int ind, long long int val){
    for(int i = ind; i <= 100000; i += (i&-i)){
        int range_end = i;
        int range_start = i-((i&-i)-1);
        assert(i >= range_start && i <= range_end);
        v[i] += val;
    }
}

/// Sum of all indicies from 0 to ind inclusive
long long int sum(int ind){
    long long int rez = 0;
    while(ind != 0){
        int p = ind&(-ind);
        rez += v[ind];
        ind ^= p;
    }
    return rez;
}


/// Binary search implicit partial sums
/// Implicit because they aren't stored anywhere
/// To get the partial sum up to i you must call sum(i)
/// Note: Because all elements in the vector are positive the partial sums are ordered in a strictly increasing order
int bins(int left, int len, long long int val){
    if(len <= 0) return -1;
    if(len == 1){
        if(sum(left) == val) return left;
        else return -1;
    }
    int mid = (len/2)+left;
    long long int probe_val = sum(mid);
    if(probe_val == val) return mid;
    else if(probe_val < val)
        return bins(mid+1, len-(mid-left+1), val);
    else if(probe_val > val)
        return bins(left, (mid-left+1)-1, val);

    assert(false); return -1;
}

ifstream f("aib.in");
ofstream g("aib.out");

int main() {
f >> N >> M;
for(int i = 1; i <= N; i++){
    long long int t;
    f >> t;
    add(i, t);
}


for(int i = 1; i <= M; i++){
    int opid;
    f >> opid;
    long long int a, b;
    if(opid == 0){
        f >> a >> b;
        add(a, b);
    }else if(opid == 1) {
        f >> a >> b;
        g << sum(b)-sum(a-1) << endl;
    }else if(opid == 2){
        f >> a;
        g << bins(1, N, a) << endl;
    }
}

}