Cod sursa(job #1194557)

Utilizator BarracudaFMI-Alex Dobrin Barracuda Data 4 iunie 2014 02:22:32
Problema Zeap Scor 100
Compilator cpp Status done
Runda Teme Pregatire ACM Unibuc 2013 Semestrul 2 Marime 3.32 kb
#include <cstdlib>
#include <ctime>
#include <cstring>
#include <algorithm>
#include <cstdio>

using namespace std;

struct node {
    int v, mindif,max, min, p;
    node *l, *r;
};

node *R, *nil;

void init () {
    nil = new node;
    nil->l = nil->r = NULL;
    nil->v= nil->max = nil->p = -0x3f3f3f3f;
    nil->mindif = nil->min = 0x3f3f3f3f;
    R = nil;
}

inline void update (node *&n) {
    if (n == nil) return;
    n->mindif = 0x3f3f3f3f;
    n->min = min (n->v, min (n->l->min, n->r->min));
    n->max = max (n->v, max (n->r->max, n->r->max));
    n->mindif = min (n->l->mindif, n->r->mindif);
    n->mindif = min (n->mindif, n->v - n->l->max);
    n->mindif = min (n->mindif, n->r->min - n->v);
}

inline void rotleft (node *&n) {
    node *t = n->l;
    n->l = t->r;
    t->r = n;
    update (n); update (t);
    n = t;
}

inline void rotright (node *&n) {
    node *t = n->r;
    n->r = t->l;
    t->l = n;
    update (n); update (t);
    n = t;
}

inline void insert (node *&n, int v) {
    if (n == nil) {
        n = new node;
        n->l = n->r = nil;
        n->v = v; n->p = rand();
        n->min = n->max = v;
        n->mindif = 0x3f3f3f3f;
        return;
    }
    if (v < n->v) {
        insert (n->l, v);
        if (n->l->p > n->p) rotleft (n);
    }
    if (v > n->v) {
        insert (n->r, v);
        if (n->r->p > n->p) rotright (n);
    }
    update (n);
}

inline int find (node *n, int v) {
    if (n == nil) return 0;
    if (v < n->v) return find (n->l, v);
    if (v > n->v) return find (n->r, v);
    if (v == n->v) return 1;
}

inline void erase (node *&n, int v) {
    if (n == nil) return;
    if (v < n->v) erase (n->l, v);
    if (v > n->v) erase (n->r, v);
    if (v == n->v) {
        if (n->l == nil && n->r == nil) {
            delete n;
            n = nil;
            return;
        }
        if (n->l->p > n->r->p) rotleft (n);
        else rotright (n);
        erase (n, v);
    }
    update (n);
}

inline int max_dif (node *n) {
    if (n == nil) return -1;
    if (n->l == nil && n->r == nil) return -1;
    return n->max - n->min;
}

inline int min_dif (node *n) {
    if (n == nil) return -1;
    if (n->l == nil && n->r == nil) return -1;
    return n->mindif;
}

void ino (node *n) {
    if (n == nil) return;
    ino (n->l);
    printf ("(%d %d %d) ", n->v, n->min, n->max);
    ino (n->r);
}

int main () {
    srand (time (0));
    init ();

    freopen ("zeap.in", "r", stdin);
    freopen ("zeap.out", "w", stdout);

    while (!feof (stdin)) {
        char ax[16];
        memset (ax, 0, sizeof (ax));
        gets (ax);
        if (ax[0] == 'M') {
            if (ax[1] == 'A') printf ("%d\n", max_dif(R));
            else printf ("%d\n", min_dif(R));
        }
        else {
            int pz = 1;
            while (ax[pz] < '0' || ax[pz] > '9') ++pz;
            int x = 0;
            while (ax[pz] >= '0' && ax[pz] <= '9')
                x = x * 10 + ax[pz] - '0', ++pz;

            if (ax[0] == 'I') insert (R, x);
            if (ax[0] == 'S') {
                if (find (R, x) == false)
                    printf ("-1\n");
                else
                    erase (R, x);
            }
            if (ax[0] == 'C') printf ("%d\n", find (R, x));
        }
    }
}