Cod sursa(job #2539039)

Utilizator giotoPopescu Ioan gioto Data 5 februarie 2020 15:56:52
Problema Secv8 Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.79 kb
#include <bits/stdc++.h>
using namespace std;

mt19937_64 rng(chrono::steady_clock::now().time_since_epoch().count());

struct data{
	int sz, rev, val;
	unsigned long long prior;

	data *l, *r;
	
	data(){sz = rev = val = prior = 0; l = r = NULL;}
};

typedef data* node;

node Treap;

void propag(node Treap){
	if(Treap != NULL && Treap->rev){
		Treap->rev = 0;
		swap(Treap->l, Treap->r);
		if(Treap->l) Treap->l->rev ^= 1;
		if(Treap->r) Treap->r->rev ^= 1;
	}
}

int get_size(node Treap){
	if(Treap == NULL) return 0;
	return Treap->sz;
}

void new_size(node Treap){
	if(Treap == NULL) return ;
	Treap->sz = get_size(Treap->l) + get_size(Treap->r) + 1;
}

int get_val(node Treap, int key, int add = 0){
	if(Treap == NULL) return 0;
	propag(Treap);

	int cur_key = add + get_size(Treap->l) + 1;
	if(cur_key == key) return Treap->val;
	else if(cur_key > key) return get_val(Treap->l, key, add);
	else return get_val(Treap->r, key, cur_key);
}

void split(node Treap, node &Left_Split, node &Right_Split, int key, int add = 0){
	if(Treap == NULL){
		Left_Split = Right_Split = NULL;
		return ;
	}
		
	propag(Treap);
	
	int cur_key = add + get_size(Treap->l);
	if(key <= cur_key){
		split(Treap->l, Left_Split, Treap->l, key, add);
		Right_Split = Treap;
	}
	else{
		split(Treap->r, Treap->r, Right_Split, key, cur_key + 1);
		Left_Split = Treap;
	}
	
	new_size(Treap);
}

void merge(node &Treap, node Left, node Right){
	propag(Left); propag(Right);
	if(Left == NULL || Right == NULL){
		Treap = Left ? Left : Right;
		return ;
	}
	
	if(Left->prior > Right->prior){
		merge(Left->r, Left->r, Right);
		Treap = Left;
	}
	else{
		merge(Right->l, Left, Right->l);
		Treap = Right;
	}
	
	new_size(Treap);
}

void reverse(int x, int y){
	node T1, T2, T3;
	split(Treap, T1, T2, x - 1);
	split(T2, T2, T3, y - x + 1);

	T2->rev ^= 1;
	
	merge(Treap, T1, T2);
	merge(Treap, Treap, T3);
}

void insert(int val, int pos){
	node T1, T2, T3;
	split(Treap, T1, T2, pos - 1);
		
	T3 = new data;
	T3->prior = rng();
	T3->sz = 1;
	T3->val = val;
	
	merge(T1, T1, T3);
	merge(Treap, T1, T2);
}

void remove(int x, int y){
	node T1, T2, T3;
	split(Treap, T1, T2, x - 1);
	split(T2, T2, T3, y - x + 1);
	merge(Treap, T1, T3);
}

void output(node Treap){
	if(Treap == NULL) return ;
	propag(Treap);
	
	output(Treap->l);
	printf("%d ", Treap->val);
	output(Treap->r);
}

int main(){
	freopen("secv8.in", "r" ,stdin);
	freopen("secv8.out", "w", stdout);
		
	int nr_op, x, y;
	char c;
	scanf("%d %d\n", &nr_op, &x);
	while(nr_op--){
		scanf("%c", &c);
		if(c == 'I'){
			scanf("%d%d\n", &x, &y);
			insert(y, x);
		}
		else if(c == 'R'){
			scanf("%d%d\n", &x, &y);
			reverse(x, y);
		}
		else if(c == 'D'){
			scanf("%d%d\n", &x, &y);
			remove(x, y);
		}
		else if(c == 'A'){
			scanf("%d\n", &x);
			printf("%d\n", get_val(Treap, x));
		}
	}
			
	output(Treap);
	return 0;
}