Cod sursa(job #1522021)

Utilizator alexpetrescuAlexandru Petrescu alexpetrescu Data 11 noiembrie 2015 08:24:40
Problema Zeap Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 4.27 kb
#include <cstdio>
#include <ctime>
#include <cstdlib>
#include <cctype>
#define nextch() fgetc(fin)
#define NIL -1
struct node{
    int val, pri, max, min, ans;
    node *st, *dr;
    node(int _val){
        val=_val;
        pri=rand();
        st=dr=NULL;
        max=min=_val;
        ans=NIL;
    }
}*root;
int f, k;
FILE *fin;
inline int read(){
    int x=0;
    char ch=nextch();
    while(!isdigit(ch)){
        ch=nextch();
    }
    while(isdigit(ch)){
        x=10*x+ch-'0';
        ch=nextch();
    }
    return x;
}
inline int max2(int a, int b){
    if(a>b){
        return a;
    }
    return b;
}
inline int min2(int a, int b){
    if(a<b){
        return a;
    }
    return b;
}
inline void refresh(node *n){
    n->ans=NIL;
    n->min=n->val;
    n->max=n->val;
    if(n->st!=NULL){
        n->min=n->st->min;
        if(n->st->ans!=NIL){
            n->ans=n->st->ans;
        }
        if((n->ans==NIL)||(n->ans>n->val-n->st->max)){
            n->ans=n->val-n->st->max;
        }
    }
    if(n->dr!=NULL){
        n->max=n->dr->max;
        if((n->dr->ans!=NIL)&&((n->ans==NIL)||(n->ans>n->dr->ans))){
            n->ans=n->dr->ans;
        }
        if((n->ans==NIL)||(n->ans>n->dr->min-n->val)){
            n->ans=n->dr->min-n->val;
        }
    }
}
inline node *rotDr(node *n){
    node *aux=n->st;
    n->st=aux->dr;
    aux->dr=n;
    refresh(n);
    refresh(aux);
    return aux;
}
inline node *rotSt(node *n){
    node *aux=n->dr;
    n->dr=aux->st;
    aux->st=n;
    refresh(n);
    refresh(aux);
    return aux;
}
inline node *balance(node *n){
    if((n->st!=NULL)&&(n->st->pri>n->pri)){
        return rotDr(n);
    }
    if((n->dr!=NULL)&&(n->dr->pri>n->pri)){
        return rotSt(n);
    }
    refresh(n);
    return n;
}
node *insert(node *n, int e){
    if(n==NULL){
        n=new node(e);
        return n;
    }
    if(e==n->val){
        return n;
    }
    if(e<n->val){
        n->st=insert(n->st, e);
    }else{
        n->dr=insert(n->dr, e);
    }
    return balance(n);
}
node *erase(node *n, int e){
    if(n==NULL){
        return NULL;
    }
    node *aux;
    if(n->val==e){
        f=0;
        if(n->st==NULL){
            if(n->dr==NULL){
                delete n;
                return NULL;
            }else{
                aux=rotSt(n);
                aux->st=erase(aux->st, e);
            }
        }else if((n->dr==NULL)||(n->dr->pri<n->st->pri)){
            aux=rotDr(n);
            aux->dr=erase(aux->dr, e);
        }else{
            aux=rotSt(n);
            aux->st=erase(aux->st, e);
        }
        return balance(aux);
    }
    if(e<n->val){
        n->st=erase(n->st, e);
    }else{
        n->dr=erase(n->dr, e);
    }
    return balance(n);
}
void find(node *n, int e){
    if(n==NULL){
        return ;
    }
    if(n->val==e){
        f=1;
        return ;
    }
    if(e<n->val){
        find(n->st, e);
    }else{
        find(n->dr, e);
    }
}
inline void adauga(int e){
    root=insert(root, e);
    k++;
}
inline int sterge(int e){
    f=NIL;
    root=erase(root, e);
    if(f!=NIL){
        k--;
    }
    return f;
}
inline int cauta(int e){
    f=0;
    find(root, e);
    return f;
}
inline int maxdif(){
    if(k<2){
        return NIL;
    }else{
        return root->max-root->min;
    }
}
inline int mindif(){
    if(k<2){
        return NIL;
    }else{
        return root->ans;
    }
}
int main(){
    srand(time(0));
    int f;
    char ch;
    FILE *fout;
    fin=fopen("zeap.in", "r");
    fout=fopen("zeap.out", "w");
    ch=nextch();
    while(ch!=EOF){
        if(ch=='I'){
            adauga(read());
        }else if(ch=='S'){
            f=sterge(read());
            if(f==NIL){
                fprintf(fout, "-1\n");
            }
        }else if(ch=='C'){
            fprintf(fout, "%d\n", cauta(read()));
        }else{
            ch=nextch();
            ch=nextch();
            if(ch=='X'){
                fprintf(fout, "%d\n", maxdif());
            }else{
                fprintf(fout, "%d\n", mindif());
            }
            ch=nextch();
        }
        ch=nextch();
    }
    fclose(fin);
    fclose(fout);
    return 0;
}