This article mainly introduces 2-3 trees, and introduces the RB tree (red-black tree) by 2-3 trees
Complete code attached
2-3 Trees
1.2-3 Trees
2-3 Tree Concept:
A 2-3 find tree, or an empty tree, or a tree consisting of 2-node, 3-node.
2-node: Contains a key value pair and two links, the left link node is smaller than the node, and the right link node is greater than the node.
3-node: Contains two key-value pairs and three links, the left-link node is less than the small key value of the nodes, the link is between the two key values of the junction, the right link is greater than the large key value of the change node.
2.2-3 Tree Lookup Add
1). Find:
Referring to the previous article, the implementation is relatively simple, that is, the comparison needs to find the key value and x.left,x.right comparison, recursive implementation.
2). Add:
Add first need to find the correct location to add;
Then the main two classes (others can be transformed out by both):
One: Add to empty node-add directly, or add to 2-node (2-node becomes 3-node implementation);
Two: Add a new key value to the 3-node tree, 1. Create a 4-node, 2. Decompose 4-nodes into two 2-node trees;
< If a parent node is a 3-node 3-node to add a new key value, the same first becomes 4-node, and then recursive to 3-node, if recursive to the node is still 4-node, the direct decomposition of the root node >
Red and black Trees
1. Red and black tree definition
Basic idea:
Use a standard two-fork lookup tree (all composed of 2-nodes) and some additional information (color: red-black) for 2-3 trees.
Among them, it satisfies the following three two-fork search trees that contain a red-black chain:
1> red links are to do links;
2> No node is composed of two red links at the same time;
3> The tree is the perfect black balance (ie: any empty link to the root node path on the same number of black links).
Red and black Tree add operation
Why is there a red and black tree rotation operation? Why are there left and right links and color conversions?
Because the tree must be guaranteed to be perfectly black and balanced.
So when it comes to the operation of a red-black tree, such as increasing:
We have to make sure that the link color of the newly added node is red. (So the tree is a red-and-black tree when you add such a knot recursively)
If the node we just added is greater than the root node, this time it needs to be rotated to the left .
And the right rotation is because there are two consecutive red links, so this time need to rotate right and then left to rotate.
* The rotation of the red and black trees *
1). Node inner class definition:
private class node { private int N; private Node Left,right; private Key key; private Value Val; boolean color; public node (Key key,value val,int n,boolean color) {this . Key = key; this . val = val; this . n = n; this . Color = color; } }
2). Left Rotation:
There are nodes with red links on the right.
The implementation is as follows:
Private node Rotateleft (node h) {nodex= h. Right;H. Right=x. Left; x. Left= h; x. Color= h. Color;H. Color= RED; x. N= h. N;H. N= Size (h. Left) + Size (h. Right)+1;Returnx;}
3). Right Rotation:
There are two contiguous left links in red.
such as: X.left = red && x.left.left = red;
Realize:
Private node Rotateright (node h) {nodex= h. Left;H. Left=x. Right; x. Right= h; x. Color= h. Color;H. Color= RED; x. N= h. N;H. N= Size (h. Left) + Size (h. Right)+1;Returnx;}
4). Color conversion
This function is a copy Web site, the original implementation needs to create two similar functions//one is used for put add operation: the node to red (because two links are red links)//one for the delete operation: the node into black, two links into red. Flip the colors of a node andIts-children private void flipcolors (Node h) {//h must has opposite color of its-children//A Ssert (h! = null) && (h. Left! = null) && (h. Right! = NULL);ASSERT (!isred (h) && isred (H. Left) && isred (H. Right)) // || (isred (h) &&!isred (H. Left) &&!isred (H. Right));H. Color=!h. Color;H. Left. Color=!h. Left. Color;H. Right. Color=!h. Right. Color;}
Add operation put implementation:
PrivateNode put (node H, key key, ValueVal) {//recursive Comparison the node insertion location //Add the nodes that are obviously going to be set to red if(H = =NULL)return NewNode (Key,Val,1, RED); int cmp = Key.compareto (H.key);if(CMP <0) H.left = put (H.left, key,Val);Else if(CMP >0) H.right = put (h.right, key,Val);ElseH.Val=Val;//Each time a recursive increment element is needed, the red and black tree needs to be repaired to guarantee three definitions. //fix-up any right-leaning links if(Isred (h.right) &&!isred (h.left)) H = rotateleft (h);if(Isred (H.left) && isred (h.left.left)) H = rotateright (h);if(Isred (H.left) && isred (h.right)) flipcolors (h); H.N = Size (h.left) + size (h.right) +1;returnH }
Red-Black Tree delete operation
When deleting an operation, we must ensure that the deletion is not a 2-node, because 2-node deletion regrets the formation of an empty link, which destroys the third definition of the red-black tree.
1. Insert algorithm for 2-3-4 tree
< This algorithm implements actions that can be transformed both upward and downward along a path >
is divided into two parts:
1> down Transformation
guarantees that the current node is not a 4-node. When a parent node is encountered with a 2-node 4-node, divide the 4-node into two 2-nodes, and pass the middle key value to the parent node (the parent node becomes the 3-node); When you encounter a 3-node with a parent node of 4-node, the same action ( at this point the parent node becomes 4-node) is flattened with an upward transform ).
2> up transforms
to trim the previously created 4-node (decomposed into three 2-nodes with a height increase of 1).
implementation of this algorithm on a red-black tree:
1> 4-node decomposition into three 2-knot tree, linked with a red link,
2> down process (recursive process) all 4-node color conversion;
3> up process, Decomposition rotation decomposes all 4-nodes (trim).
2. Delete the minimum key
by the third definition of the red and Black book, you can know that when you delete a key, if you delete a 2-node, an empty link is formed, resulting in a third definition not conforming. Therefore, when you delete the red-black tree key, the current node must be 3-node or 4-node.
Complete the above requirements, you must meet one of the circumstances:
1> If the current node is not 2-node;
2> the left Dial hand node of the current node is a 2-node, and the sibling node of the current node is not a 2-node, at which point a node is required to delete the operation;
3 > When none of the above two conditions are met, the parent node and the node adjacent to the current node are combined into 3-node or 4-node. The
three procedures, such as:
, are implemented as follows:
public void deletemin () {if (!isred (root.left) &&!isred (root.right)) Root.color = RED; Root = Deletemin (root); if (IsEmpty ()) Root.color = BLACK; } private node deletemin (Node h) {if (h.left = = null ) retur n null ; if (!isred (H.left) &&!isred (h.left.left)) H = moveredleft (h); //because it is the deletion of the minimum value operation, so if the deletion is a black link, the formation of the empty link will certainly break the balance. H.left = Deletemin (h.left); return balance (h); }
where Moveredleft (the deleted node is red) is as follows:
privatemoveRedLeft(Node h) { flipColors(h); if(isRed(h.right.left)) { //红链接往右移动,这样就保证了删除最小值h.right.left后,仍然是黑色平衡 h.right = rotateRight(h.right); //而上一部的操作,可能会让h.right结点为红色,所以修复 h = rotateLeft(h); } return h; }
where the Banlance function (after deletion, fix red black tree) is implemented as follows:
private Node Balance (node h) {if (isred (H.right )) H = rotateleft (h); if (Isred (H.left ) && isred (H.left . Span class= "hljs-built_in" >left )) H = rotateright (h); if (Isred (H.right ) &&!isred (H.left )) h = rotateleft (h); if (Isred (H.left ) && isred (H.right )) Flipcolors (h); H.N = Size (H.left ) +size (H.right ) +1 ; return h; }
3. Delete any key
Similar to removing the minimum key value, you must ensure that the deleted node is not a 2-node.
1> when the delete node is at the bottom, it can be deleted directly; not the bottom, similar to the node in the previous article that deleted the binary search tree.
After the 2> is deleted, you still need to use backtracking and decompose the remaining 4-nodes.
Realize:
Publicvoid Delete (key key) {if(! (Get(key)! =NULL)) return;if(!isred (Root). Left) &&!isred (root. Right)) Root.color = RED; Root = delete (root, key);if(!IsEmpty()) Root.color = BLACK; }PrivateNode Delete (node H, key key) {if(Key.compareto (H.key) <0) {if(!isred (H. Left) &&!isred (H. Left. Left) H = moveredleft (h); H. Left= Delete (H. Left, key); }Else{if(Isred (H. Left) H = rotateright (h);if(Key.compareto (h.key) = =0&& (H. Right==NULL)) returnNULL;if(!isred (H. Right) &&!isred (H. Right. Left) H = moveredright (h);if(Key.compareto (h.key) = =0{Node x = min (H.) Right); H.key = X.key; H.val = X.val; H. Right= Deletemin (H. Right); }ElseH. Right= Delete (H. Right, key); } return Balance (h); }
参照网站:http://algs4.cs.princeton.edu/30searching/
Algorithm version Fourth
Algorithms-Trees (2)-2-3 trees, red and black trees