Cod sursa(job #1807567)

Utilizator preda.andreiPreda Andrei preda.andrei Data 16 noiembrie 2016 18:25:27
Problema Heapuri Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.86 kb
#include <fstream>
#include <vector>

using namespace std;

typedef vector<pair<int, int>> Heap;
typedef unsigned int uint;

inline uint Tata(int x) { return x / 2; }
inline uint FiuSt(int x) { return x * 2; }
inline uint FiuDr(int x) { return x * 2 + 1; }

void Percolate(Heap &h, vector<int> &poz, int p)
{
    while (p > 0 && h[p] < h[Tata(p)]) {
        swap(poz[h[p].second], poz[h[Tata(p)].second]);
        swap(h[p], h[Tata(p)]);
        p = Tata(p);
    }
}

void Sift(Heap &h, vector<int> &poz, int p)
{
    while (p != -1) {
        int fiu = -1;
        if (FiuSt(p) < h.size()) {
            fiu = FiuSt(p);
            if (FiuDr(p) < h.size() && h[FiuDr(p)] < h[fiu]) fiu = FiuDr(p);
            if (h[fiu] < h[p]) {
                swap(h[fiu], h[p]);
                swap(poz[h[fiu].second], poz[h[p].second]);
            } else {
                fiu = -1;
            }
        }
        p = fiu;
    }
}

void Adauga(Heap &h, vector<int> &poz, int x)
{
    poz.push_back(h.size());
    h.push_back({x, poz.size() - 1});
    Percolate(h, poz, h.size() - 1);
}

void Sterge(Heap &h, vector<int> &poz, int x)
{
    unsigned p = poz[x];
    poz[h.back().second] = p;
    swap(h[p], h.back());
    h.pop_back();

    if (p != h.size()) {
        if (p > 0 && h[Tata(p)] > h[p])
            Percolate(h, poz, p);
        else Sift(h, poz, p);
    }
}

int main()
{
    ifstream fin("heapuri.in");
    ofstream fout("heapuri.out");

    int n;
    fin >> n;

    Heap heap;
    vector<int> poz{0};
    while (n--) {
        int r;
        fin >> r;
        if (r == 3) {
            fout << heap[0].first << "\n";
        } else {
            int x;
            fin >> x;
            if (r == 1)
                Adauga(heap, poz, x);
            else Sterge(heap, poz, x);
        }
    }

    return 0;
}