Cod sursa(job #1473034)

Utilizator andrei.arnautuAndi Arnautu andrei.arnautu Data 18 august 2015 13:16:11
Problema Zeap Scor 10
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.89 kb
/**
  *  Worg
  */
#include <ctime>
#include <cstdio>
#include <cstdlib>
#include <algorithm>

#define inf 2000000000

using namespace std;
FILE *fin=freopen("zeap.in","r",stdin);
FILE *fout=freopen("zeap.out","w",stdout);

int nodes;
char s[20];

struct treap{

        int key, priority, minim, maxim, difMin;
        treap *left, *right;

        treap(int key, int priority, int minim, int maxim, int difMin, treap *left, treap *right) {

            this -> key = key, this -> priority = priority;
            this -> minim = minim, this -> maxim = maxim, this -> difMin = difMin;
            this -> left = left, this -> right = right;
        }
} *root, *empty;

void update(treap *&node) {

    node->maxim = max(node->key, node->right->maxim);
    node->minim = min(node->key, node->left->minim);
    node->difMin = min(min(node->left->difMin, node->right->difMin),
                       min(abs(node->key - node->left->maxim), abs(node->key - node->right->minim)));
}

void rotLeft(treap *&node) {

    treap *t = node->left;
    node->left = t->right, t->right = node;
    node = t;

    if(node != empty && node->right != empty)
        update(node->right);
}

void rotRight(treap *&node) {

    treap *t = node->right;
    node->right = t->left, t->left = node;
    node = t;

    if(node != empty && node->left != empty)
        update(node->left);
}

void balance(treap *&node) {

    if(node->key < node->left->key)
        rotLeft(node);
    else if(node->key < node->right->key)
        rotRight(node);
    update(node);
}

void insert(treap *&node, int key, int priority) {

    if(node == empty) {
        node = new treap(key, priority, inf, -inf, inf, empty, empty);
        ++nodes;
        return;
    }

    if(key < node->key)
        insert(node->left, key, priority);
    else if(key > node->key)
        insert(node->right, key, priority);
    balance(node);
}

void erase(treap *&node, int key) {

    if(node == empty)
        return;
    if(key < node->key)
        erase(node->left, key);
    else if(key > node->key)
        erase(node->right, key);
    else {

        if(node->left == empty && node->right == empty)
            delete node, node = empty, --nodes;
        else {
            (node->left->priority > node->right->priority) ? rotLeft(node) : rotRight(node);
            erase(node, key);
        }
    }
    if(node != empty)
        update(node);
}

int search(treap *node, int key) {

    if(node == empty)
        return 0;
    if(node->key == key)
        return 1;
    if(key < node->key)
        return search(node->left, key);
    else
        return search(node->right, key);
}

void init() {

    srand(unsigned(time(0)));
    root = empty = new treap(0, 0, inf, -inf, inf, NULL, NULL);
}

int main() {

    init();

    int x;
    while( gets(s) ) {

        if(s[0] == 'I') {

            x = 0;
            for(int i = 2; s[i] != NULL; ++i)
                x = x * 10 + s[i] - '0';
            insert(root, x, rand() % inf + 1);
        }

        else if(s[0] == 'S') {

            x = 0;
            for(int i = 2; s[i] != NULL; ++i)
                x = x * 10 + s[i] - '0';
            if( !search(root, x) )
                printf("-1\n");
            else
                erase(root, x);
        }

        else if(s[0] == 'C') {

            x = 0;
            for(int i = 2; s[i] != NULL; ++i)
                x = x * 10 + s[i] - '0';
            printf("%d\n", search(root, x));
        }

        else if(s[1] == 'A') {

            if(nodes < 2)
                printf("-1\n");
            else
                printf("%d\n", root->maxim - root->minim);
        }

        else {
            if(nodes < 2)
                printf("-1\n");
            else
                printf("%d\n", root->difMin);
        }
    }
    return 0;
}