Cod sursa(job #2413839)

Utilizator triscacezarTrisca Vicol Cezar triscacezar Data 23 aprilie 2019 19:08:09
Problema Zeap Scor 70
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.04 kb
#include <bits/stdc++.h>


using namespace std;

ifstream f("zeap.in");
ofstream g("zeap.out");

namespace Treap{
    struct Node{
        Node *l=0,*r=0;
        int x=0;
        int y=0;
        int sz=0;
        int _min=0;
        int _max=0;
        int _mindst=0;
        Node(int _x=0): x(_x), y(rand()), sz(1), _min(1), _max(1), _mindst(1) {}
        void recalc();
    };
    int cnt(Node* t){
        if(!t)return 0;
        return (t->sz);
    }
    void Node::recalc(){
        sz=cnt(l)+cnt(r)+1;
        int l_min=(l!=0)?l->_min:  1e9 ;
        int l_max=(l!=0)?l->_max:-(1e9);
        int l_mindst=(l!=0)?l->_mindst:1e9;
        int r_min=(r!=0)?r->_min:  1e9 ;
        int r_max=(r!=0)?r->_max:-(1e9);
        int r_mindst=(r!=0)?r->_mindst:1e9;
        _min=min(x,min(l_min,r_min));
        _max=max(x,max(l_max,r_max));
        _mindst=min(min(x-l_max,r_min-x),min(l_mindst,r_mindst));
    }
    pair<Node*,Node*> split(Node* t,int val){
        if(!t)return {};
        t->recalc();
        if(t->x<=val){
            auto pa=split(t->r,val);
            t->r=pa.first;
            t->recalc();
            return {t,pa.second};
        }else{
            auto pa=split(t->l,val);
            t->l=pa.second;
            t->recalc();
            return {pa.first,t};
        }
        return {};
    }
    Node* join(Node* l,Node* r){
        if(!l)return r;
        if(!r)return l;
        l->recalc();
        r->recalc();
        if(l->y > r->y){
            l->r=join(l->r,r);
            l->recalc();
            return l;
        }else{
            r->l=join(l,r->l);
            r->recalc();
            return r;
        }
    }
    Node* insert(Node* t,int val){

        auto pa=split(t,val-1);
        auto u =split(pa.second,val);
        return join(pa.first,join(new Node(val),u.second));
    }
    Node* erase(Node* t,int val){

        auto pa=split(t,val-1);
        auto u =split(pa.second,val);
        if(!u.first)g<<-1<<'\n';
        return join(pa.first,u.second);
    }
    bool find(Node* t,int val){
        if(!t)return 0;
        if(t->x==val)return 1;
        if(t->x<val)return find(t->r,val);
        return find(t->l,val);
    }
}

int main()
{
    srand(time(0));
    Treap::Node *root=0;
    string c;
    while(f>>c){
        if(c[0]=='I'){
            int val;f>>val;
            root=Treap::insert(root,val);
        }
        if(c[0]=='S'){
            int val;f>>val;
            root=Treap::erase(root,val);
        }
        if(c[0]=='C'){
            int val;f>>val;
            g<<Treap::find(root,val)<<'\n';
        }
        if(c[0]=='M'&&c[1]=='A'){
            root->recalc();
            if(cnt(root)<=1)
                g<<-1<<'\n';
            else
                g<<(root->_max-root->_min)<<'\n';
        }
        if(c[0]=='M'&&c[1]=='I'){
            root->recalc();
            if(cnt(root)<=1)
                g<<-1<<'\n';
            else
                g<<(root->_mindst)<<'\n';
        }
    }
    return 0;
}