Cod sursa(job #2146439)

Utilizator DanizisSpartanulDani Mocanu DanizisSpartanul Data 27 februarie 2018 23:30:51
Problema Datorii Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.25 kb
#include <bits/stdc++.h>

using namespace std;

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

const int NMax=15005;

class SegmentTree
{
    public:SegmentTree(int size)
    {
        N=size;
        int lg=ceil(log2(N));
        ST.resize(1<<lg+1);
    }
    public:void Insert(int index,int value)
    {
        Insert(index,value,1,1,N);
    }
    public:void Update(int index,int value)
    {
        Update(index,value,1,1,N);
    }
    public:int Query(int start,int finish)
    {
        return Query(start,finish,1,N,1);
    }

    private:int N;
    private:vector<int> ST;

    private:void Insert(int index,int value,int node,int left,int right)
    {
        if(left==right)
        {
            ST[node]=value;
            return;
        }
        int middle=(left+right)/2;
        if(index<=middle)
            Insert(index,value,2*node,left,middle);
        else
            Insert(index,value,2*node+1,middle+1,right);
        ST[node]=ST[2*node]+ST[2*node+1];
    }

    private:void Update(int index,int value,int node,int left,int right)
    {
        if(left==right)
        {
            ST[node]-=value;
            return;
        }
        int middle=(left+right)/2;
        if(index<=middle)
            Update(index,value,2*node,left,middle);
        else
            Update(index,value,2*node+1,middle+1,right);
        ST[node]=ST[2*node]+ST[2*node+1];
    }

    private:int Query(int start,int finish,int left, int right, int node=1)
    {
        if(start<=left && finish>=right)
            return ST[node];
        int middle=(left+right)/2;
        int ret=0;
        if(start<=middle)
            ret+=Query(start,finish,left,middle,2*node);
        if(finish>middle)
            ret+=Query(start,finish,middle+1,right,2*node+1);
        return ret;
    }
};

int N,M;

int main()
{
    fin>>N>>M;

    SegmentTree segmentTree(N);
    for(int i=1;i<=N;i++)
    {
        int x;
        fin>>x;
        segmentTree.Insert(i,x);
    }

    for(int i=1;i<=M;i++)
    {
        int op,a,b;
        fin>>op>>a>>b;
        if(op==0)
            segmentTree.Update(a,b);
        if(op==1)
            fout<<segmentTree.Query(a,b)<<"\n";
    }

    return 0;
}