Cod sursa(job #1590350)

Utilizator chiriacandrei25Chiriac Andrei chiriacandrei25 Data 4 februarie 2016 22:08:56
Problema Secv8 Scor 25
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.87 kb
#include <bits/stdc++.h>
#define VAL 1000000007

using namespace std;
ofstream fout("secv8.out");

struct T
{
    T *left, *right;
    int pr,cnt,inv,val;
    T(int x)
    {
        val=x; inv=0;
        left=right=0;
        cnt=1;
        pr=rand()%VAL;
    }
} *root = 0;

inline void Push(T* nod)
{
    if(!nod) return;
    if(!nod->inv) return;
    if(nod->left) nod->left->inv^=1;
    if(nod->right) nod->right->inv^=1;
    swap(nod->left,nod->right);
    nod->inv=0;
}

inline int Cnt(T* nod)
{
    if(!nod) return 0;
    return nod->cnt;
}

inline void Upd(T* nod)
{
    if(!nod) return;
    nod->cnt=1+Cnt(nod->left)+Cnt(nod->right);
}

pair <T*,T*> Split(T* nod, int poz)
{
    if(!nod) return make_pair((T*) 0 , (T*) 0);
    pair <T*,T*> spl;
    Push(nod);

    if(Cnt(nod->left)+1 == poz)
    {
        spl.second=nod->right;
        nod->right=0;
        Upd(nod);
        spl.first=nod;
        return spl;
    }

    if(Cnt(nod->left)+1 > poz)
    {
        spl=Split(nod->left,poz);
        nod->left=spl.second; spl.second=nod;
        Upd(nod);
        return spl;
    }

    spl=Split(nod->right,poz-Cnt(nod->left)-1);
    nod->right=spl.first; spl.first=nod;
    Upd(nod);
    return spl;
}

inline T* Merge(T* L, T* R)
{
    Push(L); Push(R);

    if(!L) return R;
    if(!R) return L;

    if(L->pr <= R->pr)
    {
        R->left=Merge(L,R->left);
        Upd(R);
        return R;
    }
    else
    {
        L->right=Merge(L->right,R);
        Upd(L);
        return L;
    }
}

inline T* Find(T* nod, int poz)
{
    Push(nod);
    if(Cnt(nod->left)+1==poz) return nod;
    if(Cnt(nod->left)+1<poz) return Find(nod->right,poz-Cnt(nod->left)-1);
    return Find(nod->left,poz);
}

inline void Afis(T* nod)
{
    if(!nod) return;
    Push(nod);
    Afis(nod->left); fout<<nod->val<<" "; Afis(nod->right);
}

int main()
{
    int n,m,poz,val,st,dr;
    char tip;
    ifstream cin("secv8.in");
    cin>>n>>m;
    while(n--)
    {
        cin>>tip;
        if(tip=='I')
        {
            cin>>poz>>val;
            pair <T*,T*> spl=Split(root,poz-1);
            root=Merge(Merge(spl.first,new T(val)),spl.second);
        }
        if(tip=='A')
        {
            cin>>poz;
            fout<<Find(root,poz)->val<<"\n";
        }
        if(tip=='R')
        {
            cin>>st>>dr;
            pair <T*,T*> spl=Split(root,st-1);
            pair <T*,T*> spl1=Split(spl.second,dr);
            spl1.first->inv^=1;
            root=Merge(Merge(spl.first,spl1.first),spl1.second);
        }
        if(tip=='D')
        {
            cin>>st>>dr;
            pair <T*,T*> spl=Split(root,st-1);
            pair <T*,T*> spl1=Split(spl.second,dr-st+1);
            root=Merge(spl.first,spl1.second);
        }
    }
    Afis(root);
    fout<<"\n";
    return 0;
}