Cod sursa(job #1261705)

Utilizator gerd13David Gergely gerd13 Data 12 noiembrie 2014 17:19:00
Problema Arbori indexati binar Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.34 kb
#include <cstdio>
#include <cstring>


using namespace std ;

const char in[] = "aib.in" ;
const char out[] = "aib.out" ;
const int NMAX = 100005 ;


int N, M;
int A[NMAX] ;

inline int min(int a, int b)
{
    return (a > b ? b : a) ;
}

inline int max(int a, int b)
{
    return (a < b ? b : a) ;
}


void UPDATE(int , int ) ;
int  SEARCH(int) ;
int QUERY(int) ;

inline void UPDATE(int i, int nr)
{
    int c = 0 ;

    while(i <= N)
    {
        A[i] = A[i] + nr ;

        while( !(i & (1<<c)))
            c++ ;
        i = i + (1<<c) ;

        c += 1 ;
    }

}

inline int QUERY(int a)
{
    int c = 0, s = 0 ;

    while(a > 0)
    {

        s = s + A[a] ;

        while(!(a & (1 << c)))
            c++ ;

        a = a - (1 << c) ;
        c += 1 ;
    }

    return s ;
}

int SEARCH(int a)
{

    int pozitie = N + 1, aux  = N;
    int st = 0 ;
    int dr = N + 1 ;

    int sum = QUERY(aux) ;

    if(sum == a) pozitie = N ;

    while(aux)
    {

        aux = (st + dr) >> 1 ;

        sum = QUERY(aux) ;

        if(sum > a)
        {
            if(dr > aux) dr = aux ;
            aux  = aux - 1 ;
        }
        else if(sum == a)
        {
            pozitie = min(pozitie, aux) ;
            dr = aux ;
            aux = aux  - 1 ;
        }
        else
        {
            if(st < aux)
            {
                st = aux ;
            }

            aux += 1 ;
        }

        if(aux <= st || aux >= dr) break ;


    }

    if(pozitie == N + 1)
        return -1 ;
    else return pozitie ;

}

int main()
{

    freopen(in, "r", stdin) ;
    freopen(out, "w", stdout) ;

    scanf("%d%d", &N, &M) ;

    for(int i = 1 ; i <= N ; ++ i)
    {
        int nr ;
        scanf("%d", &nr) ;
        UPDATE(i, nr) ;
    }

    for(int i = 1 ; i <= M ; ++ i)
    {
        int tip ;
        scanf("%d", &tip) ;
        int X, Y, cc ;
        if(tip == 0)
            {scanf("%d%d", &X, &Y) ;
            UPDATE(X, Y) ;
            }

        if(tip == 1)
           {
               scanf("%d%d", &X, &Y) ;
            printf("%d\n", QUERY(Y) - QUERY(X - 1)) ;
           }

        if(tip == 2)
            {scanf("%d", &cc) ;
            printf("%d\n", SEARCH(cc)) ;
            }


    }

    return  0 ;
}