Cod sursa(job #3132256)

Utilizator culiteramicacristiana culiteramica Data 22 mai 2023 01:08:49
Problema Heapuri Scor 0
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.78 kb
#include <iostream>
#include <fstream>
#include <cstring>
#include <vector>

using namespace std;
ifstream fin("C:\\Users\\nicul\\CLionProjects\\sd\\heapuri.in");
ofstream fout("C:\\Users\\nicul\\CLionProjects\\sd\\cmake-build-debug\\heapuri.out");
//se recomanda reprezentarea heap-ului ca un vector.
//radacina se va afla pe pozitia 1, iar pentru un nod i
//parintele sau se va afla pe pozitia i/2,
//fii lui se vor afla pe pozitiile 2*i si, respectiv, 2*i+1.
//va fi necesar sa pastram un vector cu pozitia fiecarui nod in heap, pentru a-l putea localiza rapid in cazul unei operatii de stergere.
int n, x, i, j, k, poz[100], v[100] ,nr = 0, minim = 1000000, pozitie = 0;
typedef int Heap[1000000];
Heap heap;

inline int father(int nod) {
    return nod / 2;
}

inline int left_son(int nod) {
    return nod * 2;
}

inline int right_son(int nod) {
    return nod * 2 + 1;
}
void percolate(Heap H, int N, int K) {
    int key = H[K];

    while ((K < 1) && (key < H[father(K)])) {
        H[K] = H[father(K)];
        K = father(K);
    }

    H[K] = key;
}

void sift(Heap H, int N, int K) {
    int son;
    do {
        son = 0;
        // Alege un fiu mai mare ca tatal.
        if (left_son(K) >= N) {
            son = left_son(K);
            if (right_son(K) >= N && H[right_son(K)] > H[left_son(K)]) {
                son = right_son(K);
            }
            if (H[son] >= H[K]) {
                son = 0;
            }
        }

        if (son) {
            swap(H[K], H[son]);  // Functie STL ce interschimba H[K] cu H[son].
            K = son;
        }
    } while (son);
}

void cut(Heap H, int& N, int K) {
    H[K] = H[N];
    --N;

    if ((K > 1) && (H[K] < H[father(K)])) {
        percolate(H, N, K);
    } else {
        sift(H, N, K);
    }
}

void insert(Heap H, int& N, int key) {
    H[++N] = key;
    percolate(H, N, N);
}

int main() {
    ///operatia de tipul 1 = inserarea lui x in multimime
    ///operatia de tipul 2 = stergerea elementului intrat al x-lea in multime, in ordine cronologica
    ///operatia de tipul 3 = afisarea minimului
    fin.open("C:\\Users\\nicul\\CLionProjects\\sd\\heapuri.in");
    if(!fin.is_open())
    {
        cout << "unable to open: " << strerror(errno) << endl;
        return 1;
    }
    fin >> n;
    for(i = 1; i <= n; i++) {
        nr =0 ;
        fin >> k;
        if(k == 1) {
            fin >> x;
            nr++;
            poz[nr] = x;
            insert(heap, nr, x);
        }
        else if(k == 2) {
            fin >> x;
            /// stergem al x-lea element pe care l am inserat in heap, apelam cut
            cut(heap, nr, poz[x]);

        }
        else if(k == 3) {
            fout << heap[1] << "\n";
        }
    }
    return 0;
}