Cod sursa(job #2243500)

Utilizator HumikoPostu Alexandru Humiko Data 20 septembrie 2018 18:50:46
Problema Zeap Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 6.39 kb
#include <bits/stdc++.h>
#define oo 2e9+5

using namespace std;

ifstream fin ("zeap.in");
ofstream fout ("zeap.out");

char ch;

class TREAP
{
    public:
        struct treaps
        {
            treaps *left;
            treaps *right;
            int minimum;
            int maximum;
            int minimumdif;
            int value;
            int weight;

            treaps (treaps *leftson, treaps *rightson, int minimum1, int maximum1, int minimumdif1, int value1, int weight1 )
            {
                this->left = leftson;
                this->right = rightson;
                minimum = minimum1;
                maximum = maximum1;
                minimumdif = minimumdif1;
                value = value1;
                weight = weight1;
            }
        };

        treaps *root, *NILL;

        TREAP ()
        {
            srand(time(NULL));
            NILL = new treaps(NULL, NULL, 0, 0, 0, 0, 0);
            root = NILL;
        }

        int minDif()
        {
            if ( root->minimumdif && root->minimumdif != oo )
                return root->minimumdif;
            return -1;
        }

        int maxDif()
        {
            if ( root->maximum != root->minimum )
                return root->maximum-root->minimum;
            return -1;
        }

        void updateTreap( treaps *&node )
        {
            if ( node == NILL )
                return;

            node->minimum = node->value;
            node->maximum = node->value;
            node->minimumdif = oo;

            if ( node->left != NILL )
            {
                node->minimum = min(node->left->minimum, node->minimum);
                node->maximum = max(node->left->maximum, node->maximum);
                node->minimumdif = min(min(node->minimumdif, node->value-node->left->maximum),
                                      node->left->minimumdif);
            }

            if ( node->right != NILL )
            {
                node->minimum = min(node->right->minimum, node->minimum);
                node->maximum = max(node->right->maximum, node->maximum);
                node->minimumdif = min(min(node->minimumdif, node->right->minimum-node->value),
                                       node->right->minimumdif);
            }
        }

        void rotateRightNode( treaps *&node )
        {
            updateTreap(node);
            treaps *aux = node->right;
            node->right = aux->left;
            aux->left = node;
            node = aux;
            updateTreap(node->left);
            updateTreap(node->right);
            updateTreap(node);
        }

        void rotateLeftNode ( treaps *&node )
        {
            updateTreap(node);
            treaps *aux = node->left;
            node->left = aux->right;
            aux->right = node;
            node = aux;
            updateTreap(node->left);
            updateTreap(node->right);
            updateTreap(node);
        }

        void balance( treaps *&node )
        {
            updateTreap(node);
            if ( node->left != NILL && node->left->weight > node->weight )
                rotateLeftNode(node);
            if ( node->right != NILL && node->right->weight > node->weight )
                rotateRightNode(node);
        }

        bool findValue( treaps *&node, int value )
        {
            if ( node == NILL )
                return false;

            if ( node->value == value )
                return true;

            if ( node->value > value )
                return findValue(node->left, value);

            if ( node->value < value )
                return findValue(node->right, value);
        }

        void insertValue (treaps *&node, int value )
        {
            if ( node == NILL )
            {
                node = new treaps(NILL, NILL, value, value, oo, value, rand()%666013+1);
                return;
            }

            if ( node->value > value )
                insertValue(node->left, value);
            else
                insertValue(node->right, value);

            balance(node);
        }

        void eraseValue (treaps *&node, int value )
        {
            if ( node->value > value )
            {
                eraseValue(node->left, value);
                balance(node);
                return;
            }

            if ( node->value < value )
            {
                eraseValue(node->right, value);
                balance(node);
                return;
            }

            if ( node->left == NILL && node->right == NILL )
            {
                delete node;
                node = NILL;
                return;
            }

            if ( node->left != NILL && node->right != NILL )
            {
                if ( node->right->weight > node->left->weight )
                    rotateRightNode(node);
                else
                    rotateLeftNode(node);

                eraseValue(node, value);
            }
            else
            {
                if ( node->right != NILL )
                    rotateRightNode(node);
                else
                    rotateLeftNode(node);

                eraseValue(node, value);
            }
            balance(node);
        }
};

int main()
{
    TREAP *treap;

    treap = new TREAP();

    while ( (ch = fin.get()) && ch != EOF )
    {
        if ( ch == 'I' )
        {
            int x;
            fin>>x;

            if ( treap->findValue(treap->root, x) == false )
                treap->insertValue(treap->root, x);
        }

        if ( ch == 'S' )
        {
            int x;
            fin>>x;

            if ( treap->findValue(treap->root, x) == true )
                treap->eraseValue(treap->root, x);
            else
                fout<<"-1"<<'\n';

        }

        if ( ch == 'C' )
        {
            int x;
            fin>>x;

            if ( treap->findValue(treap->root, x) == true )
                fout<<1<<'\n';
            else
                fout<<0<<'\n';
        }

        if ( ch == 'M' )
        {
            ch = fin.get();

            if ( ch == 'A' )
                fout<<treap->maxDif()<<'\n';
            else
                fout<<treap->minDif()<<'\n';

            fin.get();
        }

        fin.get();
    }
}