红黑树的简单实现-RBTree
来源:互联网 发布:tk域名续费 编辑:程序博客网 时间:2024/06/11 23:15
红黑树是一个被广泛运用的平衡二叉树,同时满足以下规则
1.每个节点不是红色就是黑色
2.根节点为黑
3.不存在连续红节点
4.每条路径上黑色节点数相等,(空节点视为黑色)
这样一来,红黑树可以保持最长路径不超过最短路径的两倍,保持近似平衡,搜索时间复杂度是O(lgN)
下面是红黑树调节节点平衡与颜色的简介,当插入节点后出现连续红节点后,判断叔叔是否存在和叔叔的颜色,
若是叔叔存在且颜色为红时
叔叔不存在 或者 叔叔存在且颜色为黑时,如下图调整,四种情况四种旋转
下面是实现代码:
#include <iostream>using namespace std;enum Color{ RED, BLACK};template <class T>struct RBTreeNode{ RBTreeNode<T>* _left; RBTreeNode<T>* _right; RBTreeNode<T>* _parent; Color _color; T _key; RBTreeNode(T key) :_left(NULL), _right(NULL), _parent(NULL), _color(RED), _key(key) {}};template <class T>class RBTree{ typedef RBTreeNode<T> Node;public: RBTree() :_root(NULL) {} void RotateR(Node* parent) { Node* subL = parent->_left; Node* PParent = parent->_parent; Node* subLR = subL->_right; parent->_left = subLR; subL->_right = parent; parent->_parent = subL; if (subLR) { subLR->_parent = parent; } if (PParent==NULL) { _root = subL; subL->_parent = NULL; } else if (PParent->_key > parent->_key) { subL->_parent = PParent; PParent->_left = subL; } else if (PParent->_key < parent->_key) { subL->_parent = PParent; PParent->_right = subL; } } void RotateL(Node* parent) { Node* PParent = parent->_parent; Node* subR = parent->_right; Node* subRL = subR->_left; parent->_right = subRL; subR->_left = parent; parent->_parent = subR; if (subRL) { subRL->_parent = parent; } if (PParent == NULL) { _root = subR; subR->_parent = NULL; } else if (PParent->_key > parent->_key) { subR->_parent = PParent; PParent->_left = subR; } else if (PParent->_key < parent->_key) { subR->_parent = PParent; PParent->_right = subR; } } bool Insert(const T& key) { if (_root == NULL)//空树直接插入 { _root = new Node(key); _root->_color = BLACK; return true; } Node* cur = _root;//非空 从根节点开始 向下找位置 Node* parent = NULL; while (cur) { if (key == cur->_key) { return false; } else if (key < cur->_key) { parent = cur; cur = cur->_left; } else if (key>cur->_key) { parent = cur; cur = cur->_right; } } cur = new Node(key); cur->_parent = parent; if (parent->_key > key) { parent->_left = cur; } else if (parent->_key < key) { parent->_right = cur; } //调节节点颜色 while (parent&&parent->_color == RED) { Node* PParent = parent->_parent; if (PParent->_left == parent)//父亲是祖父的左 { Node* uncle = PParent->_right; if (uncle&&uncle->_color == RED)//叔叔为红 { parent->_color = uncle->_color = BLACK; PParent->_color = RED; cur = PParent; parent = cur->_parent; } else//叔叔不存在 或者叔叔为黑 { if (cur == parent->_left) { //右单旋 RotateR(PParent); PParent->_color = RED;//祖父变红 parent->_color = BLACK;//父亲变黑 } else//左右双旋 { RotateL(parent); RotateR(PParent); PParent->_color = RED;//祖父 变红 cur->_color = BLACK;//当前节点变黑 } } } else if (PParent->_right == parent)//父亲是祖父的右 { Node* uncle = PParent->_left; if (uncle&&uncle->_color == RED)//叔叔为红 { parent->_color = uncle->_color = BLACK; PParent->_color = RED; cur = PParent; parent = cur->_parent; } else//叔叔不存在 或者叔叔为黑 { if (cur == parent->_right)//cur为父亲的右 左单旋 { RotateL(PParent);//左单旋 parent->_color = BLACK;//父亲变红 PParent->_color = RED;//祖父变黑 } else { //右左双旋 RotateR(parent); RotateL(PParent); cur->_color = BLACK; PParent->_color = RED; } } }_root->_color = BLACK; }return true; } void Printf() { _printf(_root); } void _printf(Node*& root) { if (root == NULL) return; _printf(root->_left); printf("%d ",root->_key); _printf(root->_right); }protected: Node* _root;};int main(){ int a[] = {3,2,4,5,7,9,8,0,12,13,15}; /*int a[] = { 10,5,3 };*/ /*int a[] = { 10,5,8 };*/ /*int a[] = { 3,5,10 };*/ /*int a[] = { 3,10,5};*/ RBTree<int> t; for (int i = 0; i < sizeof(a) / sizeof(a[0]); i++) t.Insert(a[i]); t.Printf(); system("pause"); return 0;}
结果如下
如有不足 ,请不吝赐教
阅读全文
0 0
- 红黑树的简单实现-RBTree
- RBTree(红黑树的简单实现)
- RBTree-红黑树的实现
- 红黑树(RBTree)的实现
- 红黑树(RBTree)的分析和实现
- RBTree的模拟实现
- 二叉平衡树avlTree和红黑树rbTree的java实现
- 红黑树rbtree实现,原汁原味nginx。加深理解!
- 红黑树-RBTree
- RBTree红黑树
- RBTree----红黑树
- RBTree(红黑树)
- 红黑树--RBTree
- 红黑树【RBTree】
- 如何将 Linux 内核实现的红黑树 rbtree 运用到你的 C 程序中?
- 红黑树rbtree原理及linux内核中红黑树实现详解
- 对RBTree的总结
- RBTree的插入算法
- 【C语言】输出“*”菱形图案
- 大整数相加
- N个整数_n个一组有多少种排列组合方式
- MAC下安装多版本JDK和切换几种方式
- 广播接收者
- 红黑树的简单实现-RBTree
- C编码实践篇学习总结
- equals和==的区别
- python爬取糗事百科数据并保存到sqlite中,命令行读出
- 前端动画
- RNN模型中输入的重要性的评估
- Linux安装配置Redis CentOS 7 下安装Redis
- 虚拟机中的linux系统修改时间重启后仍然显示错误时间的解决方法
- Mybatis反向工程工具