Cod sursa(job #2336398)

Utilizator lucametehauDart Monkey lucametehau Data 5 februarie 2019 09:01:47
Problema Secv8 Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.27 kb
#include <fstream>
#include <iostream>
#include <vector>
#include <ctime>

using namespace std;

ifstream in ("secv8.in");
ofstream out ("secv8.out");

int q, x, y;
char ch;

vector <int> sol;

struct Treap {
  int k, p, nxt, rev;
  Treap *l, *r;
  Treap(int k, int p) {
    this->k = k; this->p = p;
    this->l = this->r = 0;
    this->nxt = 1; this->rev = 0;
  }
  Treap(Treap* l, Treap* r) {
    this->l = l; this->r = r;
    this->k = this->rev = 0;
    this->nxt = 1 + (l ? l->nxt : 0) + (r ? r->nxt : 0);
  }
}*R;

void update(Treap* &T) {
  if(T == 0)
    return;
  if(T->l)
    T->l->rev ^= T->rev;
  if(T->r)
    T->r->rev ^= T->rev;
  if(T->rev) {
    Treap* tmp = T->l;
    T->l = T->r;
    T->r = tmp;
    T->rev ^= 1;
  }
}

void get(Treap* &T) {
  T->nxt = 1 + (T->l ? T->l->nxt : 0) + (T->r ? T->r->nxt : 0);
}

void rot_left(Treap* &T) {
  Treap* tmp = T->l;
  T->l = tmp->r;
  tmp->r = T;
  get(T); get(tmp);
  T = tmp;
}

void rot_right(Treap* &T) {
  Treap* tmp = T->r;
  T->r = tmp->l;
  tmp->l = T;
  get(T); get(tmp);
  T = tmp;
}

void balance(Treap* &T) {
  if(T->l && T->l->p < T->p)
    rot_left(T);
  else if(T->r && T->r->p < T->p)
    rot_right(T);
  else
    get(T);
}

void insert(Treap* &T, int poz, int k, int p) {
  if(T == 0)
    T = new Treap(k, p);
  else {
    update(T); update(T->l); update(T->r);
    int val = (T->l ? T->l->nxt : 0);
    if(poz <= val)
      insert(T->l, poz, k, p);
    else
      insert(T->r, poz - val - 1, k, p);
    balance(T);
  }
}

void erase(Treap* &T) {
  if(!T->l && !T->r)
    delete T, T = 0;
  else {
    update(T); update(T->l); update(T->r);
    if(T->l && T->r) {
      if(T->l->p < T->r->p)
        rot_left(T), erase(T->r);
      else
        rot_right(T), erase(T->l);
    } else {
      if(T->l)
        rot_left(T), erase(T->r);
      else
        rot_right(T), erase(T->l);
    }
    get(T);
  }
}

void check(Treap* &T, vector <int> &v) {
  if(T) {
    update(T); update(T->l); update(T->r);
    check(T->l, v); v.push_back(T->k);
    check(T->r, v);
  }
}

Treap* search(Treap* &T, int poz) {
  update(T); update(T->l); update(T->r);
  int val = (T->l ? T->l->nxt : 0);
  if(val + 1 == poz)
    return T;
  if(poz <= val)
    return search(T->l, poz);
  return search(T->r, poz - val - 1);
}

void erase(Treap* &T, int a, int b) {
  Treap *Tl, *Tr;
  insert(T, a - 1, 0, 0);
  insert(T->r, b - a + 1, 0, 0);
  Tl = T->l; Tr = T->r->r;
  delete T->r; delete T;
  T = new Treap(Tl, Tr);
  erase(T);
}

void split(Treap* &T, int a, int b) {
  Treap *Tl, *Tr, *Tm;
  insert(T, a - 1, 0, 0);
  insert(T->r, b - a + 1, 0, 0);
  Tl = T->l; Tr = T->r->r; Tm = T->r->l;
  Tm->rev ^= 1;
  delete T->r; delete T;
  T = new Treap(Tl, Tm);
  erase(T);
  Tm = T; T = new Treap(Tm, Tr);
  erase(T);
}

int main() {
  srand((unsigned)time(0));
  in >> q >> x;
  for(; q; q--) {
    in >> ch;
    if(ch == 'I')
      in >> x >> y, insert(R, x - 1, y, rand() + 1);
    else if(ch == 'D')
      in >> x >> y, erase(R, x, y);
    else if(ch == 'A')
      in >> x, out << search(R, x)->k << "\n";
    else
      in >> x >> y, split(R, x, y);
  }
  check(R, sol);
  for(auto i : sol)
    out << i << " ";
  return 0;
}