Pagini recente » Arhiva de probleme | Cod sursa (job #1953514) | Cod sursa (job #989544) | Cod sursa (job #2771091) | Cod sursa (job #1672938)
#include<bits/stdc++.h>
template <class Te>
class SBTnode
{
public:
template <class T>
friend class SBTree;
SBTnode<Te> *p, *left, *right;
Te key;
unsigned int Size;
unsigned int account;
SBTnode(Te _key)
{
key =_key;
Size = 1;
account = 1;
left = NULL;
right = NULL;
};
};
template <class T>
class SBTree
{
public:
inline void LeftRotate(SBTnode<T> * x);
inline void RightRotate(SBTnode<T> * x);
inline SBTnode<T>* DeleteSuccessor(SBTnode<T> * x);
inline void Empty(SBTnode<T> * &x);
inline bool Insert(T & k , SBTnode<T> * &z );
inline SBTnode<T>* Search(SBTnode<T>* x , T & k);
SBTnode<T> *Root , * Nil;
unsigned int NUM;
SBTree()
{
Nil = new SBTnode<T>(0);
Nil->Size = 0;
Nil->account = 0;
Nil->left = Nil;
Nil->right = Nil;
NUM = 0;
Root = Nil;
};
~SBTree()
{
delete Nil;
Empty();
};
inline void Insert(T k);
inline void Delete(T k);
inline void Maintain(SBTnode<T> * x , bool IsRight);
inline SBTnode<T>* Search(T & k);
inline SBTnode<T>* Successor(SBTnode<T> * x);
inline SBTnode<T>* Predecessor(SBTnode<T> * x);
inline SBTnode<T>* Minimum(SBTnode<T> * x);
inline SBTnode<T>* Maximum(SBTnode<T> * x);
inline void Print(SBTnode<T> * &x);
inline void Print();
inline void Empty();
inline unsigned int Num();
};
template <class T>
void SBTree<T>::LeftRotate(SBTnode<T> * x)
{
SBTnode<T> *y = x->right;
x->right = y->left;
if(y->left != Nil)
{
y->left->p =x;
};
y->p = x->p;
if(x->p == Nil)
{
Root = y;
}else{
if(x == x->p->left)
{
x->p->left = y;
}else{
x->p->right = y;
};
};
x->p = y;
y->left = x;
y->Size = x->Size;
x->Size = x->left->Size + x->right->Size + 1;
}
template <class T>
void SBTree<T>::RightRotate(SBTnode<T> * x)
{
SBTnode<T> *y = x->left;
x->left = y->right;
if(y->right != Nil)
{
y->right->p =x;
};
y->p = x->p;
if(x->p == Nil)
{
Root = y;
}else{
if(x == x->p->right)
{
x->p->right = y;
}else{
x->p->left = y;
};
};
x->p = y;
y->right = x;
y->Size = x->Size;
x->Size = x->left->Size + x->right->Size + 1;
}
template <class T>
void SBTree<T>::Insert(T k)
{
SBTnode<T> *x = Root, *y = Nil;
while(x != Nil)
{
if(k == x->key)
{
x->account++;
NUM++;
x = x->p;
while(x != Nil)
{
x->Size--;
x = x->p;
};
return;
};
x->Size++;
y = x;
if(k < x->key)
{
x = x->left;
}else{
x = x->right;
};
};
SBTnode<T> * z = new SBTnode<T>(k);
z->p = y;
if(y == Nil)
{
Root = z;
}else{
if(k < y->key)
{
y->left = z;
}else{
y->right = z;
};
};
z->left = Nil;
z->right = Nil;
while(y != Nil)
{
Maintain(y , k >= y->key);
y = y->p;
};
}
template <class T>
void SBTree<T>::Delete(T k)
{
SBTnode<T> *z = Root, *w = Nil;
while(k != z->key && z != Nil)
{
z->Size--;
w = z;
if(k < z->key)
{
z = z->left;
}else{
z = z->right;
};
};
if(z == Nil)
{
while(w != Nil)
{
w->Size++;
w = w->p;
};
}else{
if(z->account > 1)
{
z->account--;
NUM--;
while(w != Nil)
{
w->Size++;
w = w->p;
};
return;
};
SBTnode<T> *y, *x;
if(z->left == Nil || z-> right == Nil)
{
y = z;
}else{
y = DeleteSuccessor(z);
};
if(y->left != Nil)
{
x = y->left;
}else{
x = y->right;
};
x->p = y->p;
if(y->p == Nil)
{
Root = x;
}else{
if(y == y->p->left)
{
y->p->left = x;
}else{
y->p->right = x;
};
};
if(y != z)
{
z->key = y->key;
z->account = y->account;
};
delete y;
};
}
template <class T>
SBTnode<T>* SBTree<T>::DeleteSuccessor(SBTnode<T> * x)
{
x->Size--;
x = x->right;
while(x->left != Nil)
{
x->Size--;
x = x->left;
};
return x;
}
template <class T>
void SBTree<T>::Maintain(SBTnode<T> * x , bool IsRight)
{
if(IsRight)
{
if(x->right->right->Size > x->left->Size)
{
LeftRotate(x);
}else{
if(x->right->left->Size > x->left->Size)
{
RightRotate(x->right);
LeftRotate(x);
}else{
return;
};
};
}else{
if(x->left->left->Size > x->right->Size)
{
RightRotate(x);
}else{
if(x->left->right->Size > x->right->Size)
{
LeftRotate(x->left);
RightRotate(x);
}else{
return;
};
};
};
Maintain(x->p->left,false);
Maintain(x->p->right,true);
Maintain(x->p,true);
Maintain(x->p,false);
}
template <class T>
SBTnode<T>* SBTree<T>::Successor(SBTnode<T> * x)
{
if(x->right != Nil)
return Minimum(x->right);
SBTnode<T> *y = x->p;
while(y != Nil && x == y->right)
{
x = y;
y = y->p;
};
return y;
}
template <class T>
SBTnode<T>* SBTree<T>::Predecessor(SBTnode<T> * x)
{
if(x->right != Nil)
return Minimum(x->right);
SBTnode<T> *y = x->p;
while(y != Nil && x == y->right)
{
x = y;
y = y->p;
};
return y;
}
template <class T>
SBTnode<T>* SBTree<T>::Minimum(SBTnode<T> * x)
{
while(x->left != Nil)
{
x = x->left;
};
return x;
}
template <class T>
SBTnode<T>* SBTree<T>::Maximum(SBTnode<T> * x)
{
while(x->right != Nil)
{
x = x->right;
};
return x;
}
template <class T>
SBTnode<T>* SBTree<T>::Search(T & k)
{
return Search(Root , k);
}
template <class T>
SBTnode<T>* SBTree<T>::Search(SBTnode<T>* x , T & k)
{
while(x != Nil && k != x->key)
{
if(k < x->key)
{
x = x->left;
}else{
x = x->right;
};
};
return x;
}
template <class T>
void SBTree<T>::Print(SBTnode<T> * &x)
{
if(x->left != Nil)
Print(x->left);
for(int i = 0 ; i < x->account ; i++)
{
std::cout<<x->key<<std::endl;
};
if(x->right != Nil)
Print(x->right);
}
template <class T>
void SBTree<T>::Print()
{
if(Root == Nil)
{
std::cout<<"Empty tree!"<<std::endl;
return;
};
Print(Root);
}
template <class T>
void SBTree<T>::Empty()
{
if(Root != Nil)
{
Empty(Root);
Root = Nil;
NUM = 0;
};
}
template <class T>
void SBTree<T>::Empty(SBTnode<T> * &x)
{
if(x->left != Nil)
Empty(x->left);
if(x->right != Nil)
Empty(x->right);
delete x;
}
template <class T>
unsigned int SBTree<T>::Num()
{
return (Root->Size + NUM);
}
#define BUFF 252587
char buff[BUFF];
int pos = BUFF;
inline char getChar() {
if (pos == BUFF) {
fread(buff, 1, BUFF, stdin);
pos = 0;
}
return buff[pos++];
}
inline int readInt() {
int q = 0;
char c;
do {
c = getChar();
} while (!isdigit(c));
do {
q = (10 * q) + (c - '0');
c = getChar();
} while (isdigit(c));
return q;
}
int main() {
freopen("hashuri.in", "r", stdin);
freopen("hashuri.out", "w", stdout);
int T = readInt();
SBTree <int> Q;
while (T--) {
int op = readInt(), x = readInt();
if (op == 1) {
Q.Insert(x);
} else if (op == 2) {
Q.Delete(x);
} else {
putchar((Q.Search(x)->key == x) + '0');
putchar('\n');
}
}
fclose(stdout);
return 0;
}