Cod sursa(job #2956302)

Utilizator stefan.popescuPopescu Stefan stefan.popescu Data 18 decembrie 2022 23:13:12
Problema Zeap Scor 70
Compilator cpp-32 Status done
Runda Arhiva de probleme Marime 3.68 kb
#include <bits/stdc++.h>
#include <iostream>

using namespace std;
const int inf = 1e9;

struct segObj{
    int maxi, mini, ans;
    segObj(int x = 0, int y = inf + 1, int nn = inf + 1) : maxi(x), mini(y), ans(nn) { }
    inline friend segObj operator + (const segObj & s1, const segObj & s2){
        return segObj(max(s1.maxi, s2.maxi), min(s1.mini, s2.mini), min(min(s1.ans, s2.ans), s1.maxi == 0 || s2.maxi == 0 ? inf + 1 : s2.mini - s1.maxi));
    }
};

struct segNode{
    segObj info;
    segNode * ll, * rr;
    segNode(segObj temp = segObj(), segNode * p1 = nullptr, segNode * p2 = nullptr) : info(temp), ll(p1), rr(p2) { }
};

class segTree{
private:
    segNode * root;
    const int len = inf;
public:
    segTree() : root(nullptr) { }
    void pointInsert(int x){
        insertUtil(root, 1, len, x);
    }
    int pointDelete(int x){
        return deleteUtil(root, 1, len, x);
    }
    int pointFind(int x){
        return findUtil(root, 1, len, x);
    }
    segObj rootInf(){
        return root == nullptr ? segObj() : root -> info;
    }
private:
    int findUtil(segNode * & ptr, int l, int r, int p){
        if(ptr == nullptr)
            return 0;
        if(l == r)
            return 1;
        int mij = (l + r) / 2;
        if(p <= mij)
            return findUtil(ptr -> ll, l, mij, p);
        else
            return findUtil(ptr -> rr, mij + 1, r, p);
    }
    int deleteUtil(segNode * & ptr, int l, int r, int p){
        if(ptr == nullptr)
            return -1;
        if(l == r){
            ptr -> info = segObj();
            return 0;
        }
        int t = -1;
        int mij = (l + r) / 2;
        if(p <= mij)
            t = deleteUtil(ptr -> ll, l, mij, p);
        else
            t = deleteUtil(ptr -> rr, mij + 1, r, p);
        ptr -> info = (ptr -> ll == nullptr ? ptr -> rr -> info : (ptr -> rr == nullptr ? ptr -> ll -> info : (ptr -> ll -> info + ptr -> rr -> info) ) );
        return t;
    }
    void insertUtil(segNode * & ptr, int l, int r, int p){
        if(ptr == nullptr)
            ptr = new segNode();
        if(l == r){
            ptr -> info = segObj(p, p);
            return;
        }
        int mij = (l + r) / 2;
        if(p <= mij)
            insertUtil(ptr -> ll, l, mij, p);
        else
            insertUtil(ptr -> rr, mij + 1, r, p);
        ptr -> info = (ptr -> ll == nullptr ? ptr -> rr -> info : (ptr -> rr == nullptr ? ptr -> ll -> info : (ptr -> ll -> info + ptr -> rr -> info) ) );
    }   
};

void solve(){
    segTree arb;
    string s;
    while(cin >> s){
        if(s[0] != 'M'){
            int x;
            cin >> x;
            if(s[0] == 'I')
                arb.pointInsert(x);
            else if(s[0] == 'C')
                cout << arb.pointFind(x) << "\n";
            else{
                if(arb.pointDelete(x) == -1)
                    cout << "-1\n";
            }  
        }
        else{
            if(s == "MAX"){
                auto t = arb.rootInf();
                if(t.maxi == 0 || t.maxi == t.mini)
                    cout << "-1\n";
                else
                    cout << t.maxi - t.mini << "\n";
            }
            else{
                auto t = arb.rootInf();
                if(t.maxi == 0 || t.maxi == t.mini)
                    cout << "-1\n";
                else
                    cout << t.ans << "\n";
            }
        }

    }
}

int main(){
    ios_base::sync_with_stdio(false), cin.tie(0), cout.tie(0);

    freopen("zeap.in", "r", stdin);
    freopen("zeap.out", "w", stdout);
    
    int q = 1;
    // cin >> q;
    while(q--){
        solve();
    }

    return 0;
}