Cod sursa(job #1231510)

Utilizator AlexandruValeanuAlexandru Valeanu AlexandruValeanu Data 20 septembrie 2014 20:15:45
Problema Hashuri Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 5.27 kb
#include <bits/stdc++.h>

using namespace std;

template <typename T>
class SplayTree
{
public:

    SplayTree();
    SplayTree(vector<T> &v);

    bool insert(const T& value);
    bool find(const T& value);
    bool erase(const T& value);

    void inorder();

protected:

    class Node
    {
    public:

        Node(){}

        T key;
        Node *left, *right;

        Node(const T& value);
        Node(const T value, Node *_left, Node *_right);

        void update();
    };

    Node *root, *NIL;

    Node* rotateLeft(Node *root);
    Node* rotateRight(Node *root);

    Node* splay(Node *root, const T& value);

    bool insert(Node *&root, const T& value);
    bool find(Node *&root, const T& value);
    bool erase(Node *&root, const T& value);

    void inorder(Node *root);
};

///--------------------------------------------------------------------------------------
/// begin class Node implementation

template <typename T>
SplayTree<T>::Node::Node(const T& value)
{
    this->key = value;
    this->left = nullptr;
    this->right = nullptr;
}

template <typename T>
SplayTree<T>::Node::Node(const T value, Node *_left, Node *_right)
{
    this->key = value;
    this->left = _left;
    this->right = _right;
}

template <typename T>
void SplayTree<T>::Node::update()
{
}

template <typename T>
typename SplayTree<T>::Node* SplayTree<T>::rotateRight(Node *N)
{
    Node *aux = N->left;
    N->left = aux->right;
    aux->right = N;

    aux->update();
    N->update();

    return aux;
}

template <typename T>
typename SplayTree<T>::Node* SplayTree<T>::rotateLeft(Node *N)
{
   Node *aux = N->right;
    N->right = aux->left;
    aux->left = N;

    aux->update();
    N->update();

    return aux;
}

/// end class Node implementation
///--------------------------------------------------------------------------------------

template <typename T>
SplayTree<T>::SplayTree()
{
    NIL = new Node(T());
    this->root = NIL;
}

template <typename T>
typename SplayTree<T>::Node* SplayTree<T>::splay(Node *root, const T& value)
{
    if ( root == NIL || root->key == value )
        return root;

    Node *leftTreeMax, *rightTreeMin;
    static Node header;

    header.left = header.right = NIL;
    leftTreeMax = rightTreeMin = &header;

    NIL->key = value;

    while ( true )
    {
        if ( value == root->key ) break;

        if ( value < root->key )
        {
            if ( value < root->left->key )
                root = rotateRight(root);

            if ( root->left == NIL ) break;

            rightTreeMin->left = root;
            rightTreeMin = root;
            root = root->left;
        }
        else
        {
            if ( root->right->key < value )
                root = rotateLeft(root);

            if ( root->right == NIL ) break;

            leftTreeMax->right = root;
            leftTreeMax = root;
            root = root->right;
        }
    }

    leftTreeMax->right = root->left;
    rightTreeMin->left = root->right;
    root->left = header.right;
    root->right = header.left;

    return root;
}

template <typename T>
bool SplayTree<T>::insert(const T& value)
{
    return insert(root, value);
}

template <typename T>
bool SplayTree<T>::insert(Node *&root, const T& value)
{
    if ( root == NIL )
    {
        root = new Node(value);
        root->left = root->right = NIL;
        return true;
    }

    root = splay(root, value);

    if ( root->key == value )
        return false;

    Node *newNode = new Node(value);

    if ( value < root->key )
    {
        newNode->left = root->left;
        newNode->right = root;
        root->left = NIL;

        root = newNode;
    }
    else
    {
        newNode->right = root->right;
        newNode->left = root;
        root->right = NIL;

        root = newNode;
    }

    return true;
}

template <typename T>
bool SplayTree<T>::find(const T& value)
{
    return find(root, value);
}

template <typename T>
bool SplayTree<T>::find(Node *&root, const T& value)
{
    root = splay(root, value);

    return ( root->key == value );
}

template <typename T>
bool SplayTree<T>::erase(const T& value)
{
    return erase(root, value);
}

template <typename T>
bool SplayTree<T>::erase(Node *&root, const T& value)
{
    if ( root == NIL )
        return false;

    Node *newNode, *aux = root;

    root = splay(root, value);

    if ( root->key != value )
        return false;

    if ( root->left == NIL )
        newNode = root->right;
    else
    {
        newNode = splay(root->left, value);
        newNode->right = root->right;
    }

    delete root;
    root = newNode;

    return true;
}

template <typename T>
void SplayTree<T>::inorder(Node *root)
{
    if ( root == NIL )
        return;

    inorder(root->left);
    cout << root->key << " ";
    inorder(root->right);
}

template <typename T>
void SplayTree<T>::inorder()
{
    return inorder(root);
}

int main()
{
    ifstream in("hashuri.in");
    ofstream out("hashuri.out");

    in.sync_with_stdio( false );

    int N, type, key;

    in >> N;

    SplayTree <int> T;

    for ( int k = 0; k < N; ++k )
    {
        in >> type >> key;

        if ( type == 1 )
        {
            T.insert(key);
        }

        if ( type == 2 )
        {
           T.erase(key);
        }

        if ( type == 3 )
        {
           out << T.find(key) << "\n";
        }
    }

    return 0;
}