Cod sursa(job #2863248)

Utilizator Bogdan.paun50Mandresi Bogdan Bogdan.paun50 Data 6 martie 2022 15:18:12
Problema Arbori de intervale Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.18 kb
#include <bits/stdc++.h>

using namespace std;

const int DIM = 100005;

int v[DIM], aint[4 * DIM];

void build(int node, int left, int right) {
    if (left == right) {  // frunza
        aint[node] = v[left];  // maximul pe intervalul [left, left] este v[left]
        return;
    }
    
    int mid = (left + right) / 2;
    build(2 * node, left, mid);  // recursiv pt fiul stang
    build(2 * node + 1, mid + 1, right);  // recursiv pt fiul drept
    aint[node] = max(aint[2 * node], aint[2 * node + 1]);  // determinam maximul din intervalul [left, right]
}

void update(int node, int left, int right, int pos, int val) {
    if (left == right) {  // left == pos
        aint[node] = val;
        return;
    }
    
    int mid = (left + right) / 2;
    if (pos <= mid)  // pozitia care trebuie actualizata este in jumatatea stanga
        update(2 * node, left, mid, pos, val);
    else
        update(2 * node + 1, mid + 1, right, pos, val);
    aint[node] = max(aint[2 * node], aint[2 * node + 1]);  // actualizam maximul din intervalul [left, right]
}

int query(int node, int left, int right, int qLeft, int qRight) {
    // vrem sa determinam minimul din intervalul [qLeft, qRight]
    
    if (qLeft <= left && right <= qRight) {  // intervalul curent este inclus in intervalul de query
        return aint[node];
    }
    
    int mid = (left + right) / 2;
    int res = -1000000000;
    if (qLeft <= mid)  // jumatatea stanga contine valori din intervalul de query
        res = max(res, query(2 * node, left, mid, qLeft, qRight));
    if (qRight > mid)  // jumatatea dreapta contine valori din intervalul de query
        res = max(res, query(2 * node + 1, mid + 1, right, qLeft, qRight));
        
    return res;
}

int main() {
    ifstream cin("arbint.in");
    ofstream cout("arbint.out");
    
    int n, m;
    cin >> n >> m;
    for (int i = 1; i <= n; ++i)
        cin >> v[i];
        
    build(1, 1, n);  // construim arborele de intervale pentru v
    
    for (int i = 1; i <= m; ++i) {
        int op, a, b;
        cin >> op >> a >> b;
        
        if (op == 0)
            cout << query(1, 1, n, a, b) << "\n";
        else
            update(1, 1, n, a, b);
    }
    
    
    return 0;
}