Cod sursa(job #1887845)

Utilizator hegedusPaul Hegedus hegedus Data 21 februarie 2017 19:48:22
Problema Heapuri Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.69 kb
#include <iostream>
#include <cstdio>
#define nmax 200000
using namespace std;

int n,x,test,op,opx,k,k1;
int v[nmax],poz[nmax],ord[nmax];
///v[x] - al x-lea element din heap
///poz[x] - pozitia in heap a elementului inserat al x-lea
///ord[x] - al catelea a fost introdus elementul aflat pe poz x in heap
///x=v[poz[ord[x]]]

void urcare(int x)
{
    int tata=x/2;
    while(v[x] && v[x]<v[tata])
    {
        swap(v[x],v[tata]);
        swap(ord[x],ord[tata]);
        poz[ord[x]]=x;
        poz[ord[tata]]=tata;
        x/=2;
        tata/=2;
    }
}

void coborare(int x)
{
    int fiu,fius,fiud;
    fius=2*x; fiud=2*x+1;

    if (v[fius] && (v[fius]<v[fiud] || !v[fiud])) fiu=fius;
    else if (v[fiud]) fiu=fiud;
    else fiu=0;

    while(fiu && v[x]>v[fiu])
    {
        swap(v[x],v[fiu]);
        swap(ord[x],ord[fiu]);
        poz[ord[x]]=x;
        poz[ord[fiu]]=fiu;
        x=fiu;
        fius=2*x; fiud=2*x+1;

        if (v[fius] && (v[fius]<v[fiud] || !v[fiud])) fiu=fius;
        else if (v[fiud]) fiu=fiud;
        else fiu=0;
    }
}

int main()
{
    freopen("heapuri.in","r",stdin);
    freopen("heapuri.out","w",stdout);
    scanf("%d",&op);
    for(opx=1;opx<=op;opx++)
    {
        scanf("%d",&test);
        if (test==1)
        {
            scanf("%d",&v[++n]);
            ord[n]=++k;
            poz[ord[n]]=n;
            urcare(n);
        }
        else if (test==2)
        {
            scanf("%d",&k1);
            x=poz[k1];
            v[x]=v[n];
            v[n--]=0;

            if (v[x]<v[x/2]) urcare(x);
            else coborare(x);
        }
        else printf("%d\n",v[1]);
    }
    return 0;
}