Cod sursa(job #3135659)

Utilizator mjmilan11Mujdar Milan mjmilan11 Data 3 iunie 2023 22:30:11
Problema Zeap Scor 20
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.63 kb
#include <bits/stdc++.h>
#define ll long long

using namespace std;

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

const ll NMAX = 300005;
set <ll> Zeap;
priority_queue< pair<ll, pair<ll,ll>> > pq;
/// bagam toate elementele cu -(minus) in fatza ca sa avem minimul

void Inserare(ll x){
    if(Zeap.count(x) == 0){
        Zeap.insert(x);
        if(Zeap.size() > 1){
            /// bagam in pq diferentele dllre x si elementele de langa el
            set<ll>::iterator it = Zeap.find(x);
            if(it == Zeap.begin()){ /// exceptie elementul ar fi primul
                ll diff_dr = abs(*(++it) - x);
                pq.push({-diff_dr,make_pair(*it,x)});
                return;
            }
            if((++it) == Zeap.end()){ /// exceptie elementul ar fi ultimul
                --it;
                ll diff_st = abs(*(--it) - x);
                pq.push({-diff_st,make_pair(*it,x)});
                return;
            }
            --it;
            ll diff_st = abs(*(--it) - x);
            pq.push({-diff_st,make_pair(*it,x)});
            ++it;
            ll diff_dr = abs(*(++it) - x);
            pq.push({-diff_st,make_pair(*it,x)});
            --it;
            return;
        }
    }
}

ll Sterge(ll x){
    if(Zeap.count(x) == 0) return -1;

    set<ll>::iterator it = Zeap.find(x);
    if(it == Zeap.begin()){ Zeap.erase(x); return 1337; }
    if((++it) == Zeap.end()){ Zeap.erase(x); return 1337; }
    /// nu se produce nicio diferenta noua cand sterg primul/ultimul element
    --it;

    set<ll>::iterator stanga = it;
    set<ll>::iterator dreapta = it;
    --stanga;
    ++dreapta;

    ll new_dif = abs(*stanga - *dreapta);
    pq.push({-new_dif,make_pair(*stanga,*dreapta)});
    /// noua diferenta creata este cu elementul din stanga celui sters
    /// si elementul din dreapta celui sters
    /// ca in Zuma daca stii ce zic <3
    Zeap.erase(x);

    return 1337;
}
ll Cauta(ll x){
    return Zeap.count(x);
}
ll Max_Dif(){
    /// cel mai mic si cel mai mare element produc diff maxima
    if(Zeap.size() < 2) return -1;

    ll minim = *Zeap.begin();
    ll maxim = *(--Zeap.end());

    return maxim-minim;
}
ll Min_Dif(){
    if(Zeap.size() < 2) return -1;

    while(true){
        ll Apare_NrStanga = Zeap.count(pq.top().second.first);
        ll Apare_NrDreapta = Zeap.count(pq.top().second.second);
        if(Apare_NrStanga == 0 or Apare_NrDreapta == 0) pq.pop();
        else return -pq.top().first;
        /// verific daca acea diferenta minima din varf e valida
        /// valida inseamna ca ambele elementele sunt inca in set
        /// e mai usor asa decat sa actualizez PQ de fiecare data cand sterg elemente
    }
}

ll getNumar(string lin){
    string numar = "";
    for(ll i=2;i<lin.size();i++){
        numar += lin[i];
    }
    ll num = stoi(numar);
    return num;
}

void procesare(string lin){
    if(lin[0] == 'I'){ /// inserare
        ll num = getNumar(lin);
        Inserare(num);
    }
    if(lin[0] == 'S'){ /// stergere
        ll num = getNumar(lin);
        if(Sterge(num) != 1337){
            fout << -1 << '\n';
        }
    }
    if(lin[0] == 'C'){ /// cautare
        ll num = getNumar(lin);
        fout << Cauta(num) << '\n';
    }
    if(lin[1] == 'A'){ /// maxim
        fout << Max_Dif() << '\n';
    }
    if(lin[1] == 'I'){ /// minim
        fout << Min_Dif() << '\n';
    }
}

void citire(){
    while(!fin.eof()){
        string linie;
        getline(fin,linie);
        if(linie.size() == 0) break;
        procesare(linie);
    }
}

int main()
{
    citire();
    return 0;
}