• 红黑树具体介绍三


            依据之前红黑树的原理和《算法导论》上面的伪代码,我用代码将添加和调整的代码实现了一下,如有不正确请大家指正。代码能够结合前两篇文章看。

            这次把剩下的删除结加上了,经过測试是能够使用的。


    红黑树的具体介绍一

    红黑树具体介绍二

    /*
     * =====================================================================================
     *
     *       Filename:  rbtree->h
     *
     *    Description:  red black tree
     *
     *        Version:  1->0
     *        Created:  2014年05月05日 08时48分50秒
     *       Revision:  none
     *       Compiler:  gcc
     *
     *         Author:  我叫程序员XXX  
     *        Company:  
     *
     * =====================================================================================
     */
    #ifndef __RBTREE__H
    #define __RBTREE__H
    
    #define bool int
    #define successed 0
    #define failed -1
    #define BLACK 0
    #define RED 1
    
    typedef struct _rbtree_node{
            struct _rbtree_node *p; 
            struct _rbtree_node *left;
            struct _rbtree_node *right;
            int key;
            int color;
    }*p_rbtree_node;
    
    
    struct _rbtree_node node;
    
    p_rbtree_node getNode(p_rbtree_node x); 
    bool leftRotate(p_rbtree_node *root, p_rbtree_node x); 
    bool rightRotate(p_rbtree_node *root, p_rbtree_node x);
    bool rbInert(p_rbtree_node *root, p_rbtree_node z);
    bool rbInsertFixup(p_rbtree_node *root, p_rbtree_node z);
    bool rbBuilt(void);
    bool rbTransplant(p_rbtree_node *root, p_rbtree_node u, p_rbtree_node v);
    bool rbDeleteFixup(p_rbtree_node *root, p_rbtree_node x);
    p_rbtree_node Delete(p_rbtree_node z);
    p_rbtree_node rbDelete(p_rbtree_node *root, p_rbtree_node z);
    p_rbtree_node treeMinimum(p_rbtree_node z);
    p_rbtree_node Search(int key);
    p_rbtree_node priSearch(p_rbtree_node *root, int key);
    void rbDisplay(p_rbtree_node *root);
    void Display(void);
    
    #endif



    rbtree.c

    /*
     * =====================================================================================
     *
     *       Filename:  rbtree.c
     *
     *    Description:  
     *
     *        Version:  1.0
     *        Created:  2014年05月05日 09时01分00秒
     *       Revision:  none
     *       Compiler:  gcc
     *
     *         Author:  我叫程序员XXX 
     *        Company:  
     *
     * =====================================================================================
     */
    #include "rbtree.h"
    #include <malloc.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    p_rbtree_node nil = &node;
    p_rbtree_node root;
    
    p_rbtree_node getNode(p_rbtree_node x)
    {
            x = NULL;
            x = (p_rbtree_node)malloc(sizeof(struct _rbtree_node));
            if (x == NULL)
            {
                    return NULL;
            }
            memset(x, 0, sizeof(struct _rbtree_node));
    
            return x;
    }
    
    bool leftRotate(p_rbtree_node *root, p_rbtree_node x)
    {
            p_rbtree_node y = NULL;
            y = x->right;   //set y
            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;
            y->left = x;
            x->p = y;
    
            return successed;
    }
    
    bool rightRotate(p_rbtree_node *root, p_rbtree_node x)
    {
            p_rbtree_node y = NULL;
            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->left)
                    x->p->left = y;
            else
                    x->p->right = y;
            y->right = x;
            x->p = y;
    
            return successed;
    }
    
    bool rbInsert(p_rbtree_node *root, p_rbtree_node z)
    {
            p_rbtree_node y = nil;
            p_rbtree_node x = *root;
            while (x != nil)
            {
                    y = x;
                    if (z->key < x->key)
                            x = x->left;
                    else
                            x = x->right;
            }
            z->p = y;
            if (y == nil)
            {
                    *root = z;
            }
            else if (z->key < y->key)
                    y->left = z;
            else
                    y->right = z;
            z->left = nil;
            z->right = nil;
            z->color = RED;
            rbInsertFixup(root, z);
    
            return successed;
    }
    
    bool rbInsertFixup(p_rbtree_node *root, p_rbtree_node z)
    {
            while (z->p->color == RED)
            {
                    p_rbtree_node y = NULL;
                    if (z->p == z->p->p->left)
                    {
                            y = z->p->p->right;
                            if (y->color == RED)
                            {
                                    z->p->color = BLACK;
                                    y->color = BLACK;
                                    z->p->p->color = RED;
                                    z = z->p->p;
                            }
                            else if (z == z->p->right)
                            {
                                    z = z->p;
                                    leftRotate(root, z);
                            }
                            else
                            {
                                    z->p->color = BLACK;
                                    z->p->p->color = RED;
                                    rightRotate(root, z->p->p);
                            }
                    }
                    else
                    {
                            y = z->p->p->left;
                            if (y->color == RED)
                            {
                                    z->p->color = BLACK;
                                    y->color = BLACK;
                                    z->p->p->color = RED;
                                    z = z->p->p;
                            }
                            else if (z == z->p->left)
                            {
                                    z = z->p;
                                    rightRotate(root, z);
                            }
                            else
                            {
                                    z->p->color = BLACK;
                                    z->p->p->color = RED;
                                    leftRotate(root, z->p->p);
                            }
                    }
            }
            (*root)->color = BLACK;
            return successed;
    }
    
    bool rbTransplant(p_rbtree_node *root, p_rbtree_node u, p_rbtree_node v)
    {
            if (u->p == nil)
            {
                    *root = v;
            }
            else if (u == u->p->left)
            {
                    u->p->left = v;
            }
            else
                    u->p->right = v;
            v->p = u->p;
            return successed;
    }
    
    p_rbtree_node treeMinimum(p_rbtree_node z)
    {
            while (z->left != nil)
                    z = z->left;
            return z;
    }
    
    bool rbDeleteFixup(p_rbtree_node *root, p_rbtree_node x)
    {
            p_rbtree_node w = nil;
            while (x != nil && x->color == BLACK)
            {
                    if (x == x->p->left)
                    {
                            w = x->p->right;
                            if (w->color == RED)
                            {
                                    w->color = BLACK;
                                    x->p->color = RED;
                                    leftRotate(root, x->p);
                                    w = x->p->right;
                            }
                            else if (w->right->color == BLACK && w->left->color == BLACK)
                            {
                                    w->color = RED;
                                    x = x->p;
                            }
                            else if (w->right->color == BLACK)
                            {
                                    w->left->color = BLACK;
                                    w->color = RED;
                                    rightRotate(root, w);
                                    w = x->p->right;
                            }
                            else
                            {
                                    w->right->color = BLACK;
                                    w->color = x->p->color;
                                    w->p->color = BLACK;
                                    leftRotate(root, x->p);
                                    x = nil;
                            }
                    }
                    else
                    {
                            w = x->p->left;
                            if (w->color == RED)
                            {
                                    w->color = BLACK;
                                    x->p->color = RED;
                                    rightRotate(root, x->p);
                                    w = x->p->left;
                            }
                            else if (w->left->color == BLACK && w->right->color == BLACK)
                            {
                                    w->color = RED;
                                    x = x->p;
                            }
                            else if (w->left->color == BLACK)
                            {
                                    w->color = RED;
                                    w->right->color = BLACK;
                                    leftRotate(root, w);
                                    w = x->p->left;
                            }
                            else
                            {
                                    w->color = RED;
                                    w->left->color = BLACK;
                                    w->p->color = BLACK;
                                    rightRotate(root, x->p);
                                    x = nil;
                            }
                    }
            }
            x->color = BLACK;
    }
    
    p_rbtree_node Delete(p_rbtree_node z)
    {
            return rbDelete(&root, z);
    }
    
    p_rbtree_node rbDelete(p_rbtree_node *root, p_rbtree_node z)
    {
            p_rbtree_node y = nil, x = nil;
            y = z;
            int y_original_color = y->color;
            if (z->left == nil)
            {
                    x = z->right;
                    rbTransplant(root, z, x);
    
            }
            else if (z->right == nil)
            {
                    x = z->left;
                    rbTransplant(root, z, x);
            }
            else
            {
                    y = treeMinimum(z->right);
                    y_original_color = y->color;
                    x = y->right;
                    if (y->p == z)
                    {
                            x->p = y;
                    }
                    else
                    {
                            rbTransplant(root, y, x);
                            y->right = z->right;
                            z->right->p = y;
                    }
                    rbTransplant(root, z, y);
                    y->left = z->left;
                    y->left->p = y;
                    y->color = z->color;
            }
            if (y_original_color == BLACK)
                    rbDeleteFixup(root, x);
            return z;
    }
    
    bool rbBuilt()
    {
            node.p = NULL;
            node.left = NULL;
            node.right = NULL;
            node.key = -1;
            node.color = BLACK;
            root = nil;
            p_rbtree_node n1 = getNode(n1);
            n1->key = 1;
            rbInsert(&root, n1);
    
            p_rbtree_node n2 = getNode(n2);
            n2->key = 2;
            rbInsert(&root, n2);
    
            p_rbtree_node n4 = getNode(n4);
            n4->key = 4;
            rbInsert(&root, n4);
    
            p_rbtree_node n5 = getNode(n5);
            n5->key = 5;
            rbInsert(&root, n5);
    
            p_rbtree_node n7 = getNode(n7);
            n7->key = 7;
            rbInsert(&root, n7);
    
            p_rbtree_node n8 = getNode(n8);
            n8->key = 8;
            rbInsert(&root, n8);
    
            p_rbtree_node n11 = getNode(n11);
            n11->key = 11;
            rbInsert(&root, n11);
    
            p_rbtree_node n14 = getNode(n14);
            n14->key = 14;
            rbInsert(&root, n14);
    
            p_rbtree_node n15 = getNode(n15);
            n15->key = 15;
            rbInsert(&root, n15);
    
            return successed;
    }
    
    void rbDisplay(p_rbtree_node *root)
    {
            if (*root == nil)
                    return;
            rbDisplay(&((*root)->left));
            if ((*root)->color == RED)
                    printf("key=%d, color=RED
    ", (*root)->key);
            else
                    printf("key=%d, color=BLACK
    ", (*root)->key);
            rbDisplay(&((*root)->right));
    }
    
    void rbMidDisplay(p_rbtree_node *root)
    {
            if (*root == nil)
                    return;
            if ((*root)->color == RED)
                    printf("key=%d, color=RED
    ", (*root)->key);
            else
                    printf("key=%d, color=BLACK
    ", (*root)->key);
            rbMidDisplay(&((*root)->left));
            rbMidDisplay(&((*root)->right));
    }
    
    void Display(void)
    {
            rbDisplay(&root);
            rbMidDisplay(&root);
    }


    test.c 測试文件

    *
     * =====================================================================================
     *
     *       Filename:  test.c
     *
     *    Description:  
     *
     *        Version:  1.0
     *        Created:  2014年05月05日 11时34分19秒
     *       Revision:  none
     *       Compiler:  gcc
     *
     *         Author:  我叫程序员XXX  
     *        Company:  
     *
     * =====================================================================================
     */
    #include "rbtree.h"
    #include <stdio.h>
    
    int main(void)
    {
            rbBuilt();
            Display();
            int key = 5;
            p_rbtree_node node = Search(5);
            p_rbtree_node temp = NULL;
            temp = Delete(node);
            printf("*******temp->key = %d**********
    ", temp->key);
            Display();
        
            return 0;
    }


        代码的执行截图例如以下:

        代码是通过先序和中序遍历得出的结果。

    加入删除之后的执行结果例如以下:


        我的编译系统是Linux。编译环境是gcc 版本号 4.8.2 20131212 (Red Hat 4.8.2-7) (GCC) 。后面将删除代码加入上。假设代码中有不论什么不正确的地方。请大家指出。我好及时改动,谢谢大家。

  • 相关阅读:
    spring boot在控制台输出彩色日志
    springboot之使用@ConfigurationProperties注解
    spirng boot打包成war部署
    spring boot 使用不同的profile来加载不同的配置文件
    spring boot 扩展之AutoConfigurationImportListener
    spriing boot 启动报错:Cannot determine embedded database driver class for database type NONE
    jvisualvm 远程连接jboss
    解决xshell4中文乱码
    zookeeper的简单使用
    Spring框架中InitializingBean执行顺序
  • 原文地址:https://www.cnblogs.com/lytwajue/p/6755616.html
Copyright © 2020-2023  润新知