Cod sursa(job #1813651)

Utilizator rares00Foica Rares rares00 Data 23 noiembrie 2016 09:22:47
Problema Heapuri Scor 20
Compilator cpp Status done
Runda Arhiva educationala Marime 2.27 kb
//heap de minim
#include <iostream>
#include <fstream>
#define LIM 200000
using namespace std;
ifstream in("heapuri.in");
ofstream out("heapuri.out");

void interschimba(int &a,int &b){
    int aux;
    aux=a, a=b, b=aux;
}
int tata(int x){
    return x/2;
}
int fiuSt(int x){
    return x*2;
}
int fiuDr(int x){
    return x*2+1;
}
void afiseaza(int v[],int n)
{
    for(int i=1;i<=n;++i)
        out<<v[i]<<" ";
    out<<"\n";
}

void adauga(int x,int h[],int &nrh,int ord[],int &nrord)
{
    //adauga x la final
    h[++nrh]=x;
    ord[++nrord]=nrord;

    //impinge x in sus la locul lui
    int poz=nrh;
    while(poz>1)    //cat timp are tata
    {
        if(h[poz]<h[tata(poz)])
        {
            interschimba(h[poz],h[tata(poz)]);
            interschimba(ord[poz],ord[tata(poz)]);
            poz=tata(poz);
            //ord[nrord]=tata(poz);
        }
        else
            poz=1;
    }
}

void elimina(int x,int h[],int &nrh,int ord[],int &nrord)
{
    for(int i=1;i<=nrord;++i)
        if(ord[i]==x)
            x=i,i=nrord;
    //suprapune ultimul nod peste nodul x
    h[x]=h[nrh--];

    //impinge x in jos la locul lui
    int poz=x;
    while(poz<=nrh/2)
    {
        int fiu=fiuSt(poz);
        if(fiu+1<=nrh && h[fiuSt(poz)]>h[fiuDr(poz)])
            fiu = fiuDr(poz);

        if(h[poz]>h[fiu])
        {
            interschimba(h[poz],h[fiu]);
            interschimba(ord[poz],ord[fiu]);
            poz=fiu;
        }
        else
            poz=nrh/2+1;
    }
}

int main()
{
    int n,p,x;
    int h[LIM+2],nrh=0; //heap de minim
    int ord[LIM+2],nrord=0; //vector de ordine: ord[i] - numarul de ordine al nodului i

    in>>n;
    for(int k=1;k<=n;++k)
    {
        //1 - adauga elementul x in heap
        //2 - sterge elementul intrat al x-lea in heap
        //afiseaza elementul minim din multime (radacina heapului)

        in>>p;
        if(p==1)
        {
            in>>x;
            adauga(x,h,nrh,ord,nrord);
            //afiseaza(h,nrh);
        }
        else if(p==2)
        {
            in>>x;
            elimina(x,h,nrh,ord,nrord);
            //afiseaza(h,nrh);
        }
        else if(p==3)
            out<<h[1]<<"\n";
    }

    return 0;
}