红黑树插入修正说明

红黑树插入步骤:

  1. 根据插入数据的大小将数据插入到树中;
  2. 将新插入的节点变成红色;

回忆下红黑树的条件:

  1. 根节点是黑色的
  2. 父子节点不能同时为红色
  3. 每一个节点机不是红色就是黑色,并且所有的叶子节点必须是黑色的
  4. 每个节点到它的叶子节点的所有路径上包含的黑色节点数目必须是一致的

      根据以上条件,插入节点为什么是红色的就很好理解了,首先,条件1很好满足,如果是插入的是空树,那么直接将新插入的节点变成黑色就好了。条件2可不一定能满足,条件3也是满足的,条件4也是满足的,因为红色节点并不影响此节点到叶子节点路径上黑色节点的数目。

综上所述,红黑树插入修正其实只需要满足条件2就行了。

现在根据新插入节点的父节点颜色来分析:

  1. 新插入节点的父节点是黑色的,那么,新插入的节点对于这棵树是不影响平衡的;不需要做任何操作
  2. 新插入节点的父节点是红色的,那么,这种情况是违背父子节点不能同时是红色节点的情况。

   我们再根据情况2(也就是父节点是红色节点的情况)做分析:(以下我们将新加入的节点称作N节点,父节点是F节点,叔叔节点是U节点)

根据情况2.有以下三种情况:

  1. 父亲节点是红色,叔叔节点是红色(将父亲和叔叔节点变成黑色,将祖父节点(祖父几点之前一定是黑色的)变成红色,并将祖父节点设为当前节点接着判断)
  2. 父亲节点是红色,叔叔节点是黑色,并且,新加入的节点是父亲节点是左孩子(以祖父节点为支点进行右旋转,然后交换祖父节点和父亲节点的颜色,此时当前节点还是新加入的节点)
  3. 父亲节点是红色,叔叔节点是黑色,并且,新加入的节点是父亲节点的右孩子(以父节点为支点,进行左旋转,此时父节点变成子节点了,将父节点设为当前节点)

注意:修正节点的主要思想是将影响红黑树平衡的节点不断往往上移,最后如果移到了根节点就直接将根节点变成黑色就行了。

此处有一个影藏条件,如果父亲节点是红色的,那么祖父节点就是黑色的

Case 1:如果是父亲和叔叔节点都是红色的,那么直接将他们两变成黑色的,此时,经过祖父节点的黑色节点数就多1了,此时将祖父节点变成红色(此时祖父节点可能会与他的父亲节点存在冲突,所以将祖父节点当成当前节点做进一步判断),并将祖父节点当成当前节点来处理;

Case2:如果父亲节点是红色的,而叔叔节点是黑色的,并且插入的节点是父亲节点的右孩子(时刻记住将多出来的红色往上移动),此时以父亲节点为支点进行左旋转,就将新插入的节点向上移动了(此时新插入的节点处在父亲节点的位置,而叔叔节点是不变的),但是,还是有同时为红色的父子节点,此时的情形是父亲节点是红色的,并且孩子节点是左孩子,叔叔节点还是黑色的。此时将最初的父亲节点、现在的孩子节点当成当前节点进行判断处理。而这种情形刚好是Case3的情形。

Case3:如果父亲节点是红色的,叔叔节点是黑色的,并且新插入的节点是左孩子。(这时候就要时刻记住要将多出来的红色节点往上移动,所以,可以将祖父节右旋转,但是旋转之后右边就会多出来一个黑色节点(祖父节点),并且右旋转后,原先的祖父节点变成此时的父亲节点,颜色由黑色变成红色,这种情况下,可以直接将祖父节点和父亲节点颜色交换,这样这两个问题就都解决了),此时将父亲节点和祖父节点交换颜色(就是父亲节点变成黑色,祖父节点变成红色)并以祖父节点为支点进行右旋转。

由于不会作图就不附图了,看到这篇文章的小伙伴可以自己画出来,其实只要时刻记住节点插入的原则就比较好理解了。

如果读者发现文章有问题或者想交流下,请留言。。。

猜你喜欢

转载自blog.csdn.net/maoxiaohai123/article/details/89418732