红黑树代码
# pragma once
const bool rb_red = false ;
const bool rb_black = true ;
class node {
public :
node ( int n, bool color_type = true ) : val ( n) , color ( color_type) , left ( nullptr ) , right ( nullptr ) , parent ( nullptr ) { } ;
int val;
node* left;
node* right;
node* parent;
bool color;
} ;
template < typename T >
class rbtree
{
public :
rbtree ( node* _root = nullptr ) : root ( _root) { } ;
void insert ( T x) ;
node* get_root ( ) { return root; }
node* predecessor ( node* p) ;
node* successor ( node* p) ;
void remove ( T x) ;
node* get_node ( T x) ;
private :
void left_rotate ( node* p) ;
void fix_after_insert ( node* p) ;
void right_rotate ( node* p) ;
void fix_after_remove ( node* p) ;
bool get_color ( node* p) ;
node* root;
} ;
template < typename T >
bool rbtree < T> :: get_color ( node* p)
{
if ( p == nullptr )
return rb_black;
else
return p-> color;
}
template < typename T >
node* rbtree < T> :: successor ( node* p)
{
if ( p == nullptr )
return nullptr ;
else if ( p-> right)
{
node* rbnode = p-> right;
while ( rbnode-> left)
{
rbnode = rbnode-> left;
}
return rbnode;
}
else
{
node* parent_node = p-> parent;
node* child_node = p;
while ( parent_node != nullptr && child_node == parent_node-> right)
{
child_node = parent_node;
parent_node = parent_node-> parent;
}
return parent_node;
}
}
template < typename T >
node* rbtree < T> :: predecessor ( node* p)
{
if ( p == nullptr )
return nullptr ;
else if ( p-> left)
{
node* rbnode = p-> left;
while ( rbnode-> right)
{
rbnode = rbnode-> right;
}
return rbnode;
}
else
{
node* parent_node = p-> parent;
node* child_node = p;
while ( parent_node!= nullptr && child_node == parent_node-> left)
{
child_node = parent_node;
parent_node = parent_node-> parent;
}
return parent_node;
}
}
template < typename T >
void rbtree < T> :: remove ( T x)
{
node* delet_node = get_node ( x) ;
if ( delet_node == nullptr )
return ;
if ( delet_node-> left != nullptr && delet_node-> right != nullptr )
{
node* successor_node = successor ( delet_node) ;
delet_node-> val = successor_node-> val;
delet_node = successor_node;
}
node* replace_node = delet_node-> left != nullptr ? delet_node-> left : delet_node-> right;
if ( replace_node != nullptr )
{
replace_node-> parent = delet_node-> parent;
if ( delet_node-> parent == nullptr )
{
root = replace_node;
}
else if ( delet_node == delet_node-> parent-> left)
{
delet_node-> parent-> left = replace_node;
}
else if ( delet_node == delet_node-> parent-> right)
{
delet_node-> parent-> right = replace_node;
}
if ( delet_node-> color == rb_black)
{
fix_after_remove ( replace_node) ;
}
delet_node-> left = delet_node-> right = delet_node-> parent = nullptr ;
}
else if ( delet_node-> parent == nullptr )
{
this -> root = nullptr ;
}
else
{
if ( delet_node-> color == rb_black)
{
fix_after_remove ( delet_node) ;
}
if ( delet_node == delet_node-> parent-> left)
{
delet_node-> parent-> left = nullptr ;
}
else if ( delet_node == delet_node-> parent-> right)
{
delet_node-> parent-> right = nullptr ;
}
delet_node-> parent = nullptr ;
}
}
template < typename T >
node* rbtree < T> :: get_node ( T x)
{
node* rb_node = this -> root;
while ( rb_node != nullptr )
{
if ( x < rb_node-> val)
rb_node = rb_node-> left;
else if ( x > rb_node-> val)
rb_node = rb_node-> right;
else
return rb_node;
}
return nullptr ;
}
template < typename T >
void rbtree < T> :: fix_after_insert ( node* t)
{
t-> color = rb_red;
while ( t != root && t-> parent-> color == rb_red)
{
node* parent_ptr = t-> parent;
if ( t-> parent == parent_ptr-> parent-> left)
{
node* uncle_node = parent_ptr-> parent-> right;
bool uncle_color = ( uncle_node == nullptr ? rb_black : uncle_node-> color) ;
if ( uncle_color == rb_red)
{
parent_ptr-> color = rb_black;
uncle_node-> color = rb_black;
parent_ptr-> parent-> color = rb_red;
t = parent_ptr-> parent;
}
else
{
if ( t == parent_ptr-> right)
{
t = parent_ptr;
left_rotate ( t) ;
}
t-> parent-> color = rb_black;
t-> parent-> parent-> color = rb_red;
right_rotate ( t-> parent-> parent) ;
}
}
else
{
node* uncle_node = parent_ptr-> parent-> left;
bool uncle_color = ( uncle_node == nullptr ? rb_black : uncle_node-> color) ;
if ( uncle_color == rb_red)
{
parent_ptr-> color = rb_black;
uncle_node-> color = rb_black;
parent_ptr-> parent-> color = rb_red;
t = parent_ptr-> parent;
}
else
{
if ( t == parent_ptr-> left)
{
t = parent_ptr;
right_rotate ( t) ;
}
t-> parent-> color = rb_black;
t-> parent-> parent-> color = rb_red;
left_rotate ( t-> parent-> parent) ;
}
}
}
root-> color = rb_black;
}
template < typename T >
void rbtree < T> :: fix_after_remove ( node* p)
{
while ( p!= root && p-> color == rb_black)
{
if ( p == p-> parent-> left)
{
node* brother_node = p-> parent-> right;
if ( brother_node-> color == rb_red)
{
brother_node-> color = rb_black;
p-> parent-> color = rb_red;
left_rotate ( p-> parent) ;
brother_node = p-> parent-> right;
}
if ( get_color ( brother_node-> left) == rb_black && get_color ( brother_node-> right) == rb_black)
{
brother_node-> color = rb_red;
p = p-> parent;
}
else
{
if ( brother_node-> right-> color == rb_black)
{
brother_node-> color = rb_red;
brother_node-> left-> color = rb_black;
right_rotate ( brother_node) ;
brother_node = p-> parent-> right;
}
brother_node-> color = brother_node-> parent-> color;
brother_node-> parent-> color = rb_black;
brother_node-> right-> color = rb_black;
left_rotate ( p-> parent) ;
p = root;
}
}
else
{
node* brother_node = p-> parent-> left;
if ( brother_node-> color == rb_red)
{
brother_node-> color = rb_black;
p-> parent-> color = rb_red;
right_rotate ( p-> parent) ;
brother_node = p-> parent-> left;
}
if ( get_color ( brother_node-> left) == rb_black && get_color ( brother_node-> right) == rb_black)
{
brother_node-> color = rb_red;
p = p-> parent;
}
else
{
if ( brother_node-> left-> color == rb_black)
{
brother_node-> color = rb_red;
brother_node-> right-> color = rb_black;
left_rotate ( brother_node) ;
brother_node = p-> parent-> left;
}
brother_node-> color = brother_node-> parent-> color;
brother_node-> parent-> color = rb_black;
brother_node-> left-> color = rb_black;
right_rotate ( p-> parent) ;
p = root;
}
}
}
p-> color= rb_black;
}
template < typename T >
void rbtree < T> :: insert ( T x)
{
if ( this -> root == nullptr )
{
this -> root = new node ( x, rb_black) ;
this -> root-> parent = nullptr ;
return ;
}
bool left_or_right;
node* parent = root;
node* t = root;
while ( t != nullptr )
{
parent = t;
if ( x > t-> val)
{
t = t-> right;
left_or_right = 0 ;
}
else if ( x < t-> val)
{
t = t-> left;
left_or_right = 1 ;
}
else
return ;
}
t = new node ( x, rb_red) ;
if ( left_or_right)
parent-> left = t;
else
parent-> right = t;
t-> parent = parent;
fix_after_insert ( t) ;
}
template < typename T >
void rbtree < T> :: left_rotate ( node* p)
{
node* rbnode = p-> right;
rbnode-> parent = p-> parent;
p-> right = rbnode-> left;
if ( rbnode-> left != nullptr )
rbnode-> left-> parent = p;
if ( p == root)
root = rbnode;
else if ( p == p-> parent-> left)
p-> parent-> left = rbnode;
else if ( p == p-> parent-> right)
p-> parent-> right = rbnode;
rbnode-> left = p;
p-> parent = rbnode;
}
template < typename T >
void rbtree < T> :: right_rotate ( node* p)
{
node* rbnode = p-> left;
rbnode-> parent = p-> parent;
p-> left = rbnode-> right;
if ( rbnode-> right != nullptr )
rbnode-> right-> parent = p;
if ( p == root)
root = rbnode;
else if ( p == p-> parent-> left)
p-> parent-> left = rbnode;
else
p-> parent-> right = rbnode;
rbnode-> right = p;
p-> parent = rbnode;
}
测试函数(插入)
# include <iostream>
# include <queue>
# include "rbtree.h"
# include <string>
using namespace std;
string to_rb_color ( bool color_type)
{
if ( color_type)
return "<黑>" ;
else
return "<红>" ;
}
void output_impl ( node* n, bool left, string const & indent)
{
if ( n-> right)
{
output_impl ( n-> right, false , indent + ( left ? "| " : " " ) ) ;
}
cout << indent;
cout << ( left ? '\\' : '/' ) ;
cout << "-----" ;
cout << n-> val << to_rb_color ( n-> color) << endl;
if ( n-> left)
{
output_impl ( n-> left, true , indent + ( left ? " " : "| " ) ) ;
}
}
void output ( node* root)
{
if ( root == nullptr )
return ;
if ( root-> right)
{
output_impl ( root-> right, false , "" ) ;
}
cout << root-> val << to_rb_color ( root-> color) << endl;
if ( root-> left)
{
output_impl ( root-> left, true , "" ) ;
}
}
int main ( )
{
rbtree< int > tree;
int n = 20 ;
int x = 1 ;
while ( n-- )
{
tree. insert ( x) ;
x += 2 ;
}
output ( tree. get_root ( ) ) ;
return 0 ;
}
测试结果(插入)
测试函数(删除)
int main ( )
{
rbtree< int > tree;
int n = 20 ;
int x = 1 ;
while ( n-- )
{
tree. insert ( x) ;
x += 2 ;
}
tree. remove ( 15 ) ;
tree. remove ( 7 ) ;
tree. remove ( 29 ) ;
output ( tree. get_root ( ) ) ;
return 0 ;
}
测试结果(删除)