• C++实现红黑树(插入功能)


    practice1.h

    #ifndef PRACTICE1_H_INCLUDED
    #define PRACTICE1_H_INCLUDED
    
    template<class Comparable>
    class RedBlackTree;
    
    template<class Comparable>
    class RedBlackNode;
    
    template<class Comparable>
    class RedBlackTree
    {
    public:
        RedBlackTree(const Comparable& negInf);//伪根数据负无穷
        ~RedBlackTree();
        enum{RED,BLACK};
        typedef RedBlackNode<Comparable>  Node;
        void insert(const Comparable & x);
    //private:为了测试临时变成public
    public:
        Node *header;
        Node *nullNode;//空节点
    
        Node *current;
        Node *parent;//父节点
        Node *grand;//祖父节点
        Node *great;//曾祖父节点
    
        void rotateWithLeftChild(Node* &k2) const;
        void rotateWithRightChild(Node* &k1) const;
        void doubleRotateWithLeftChild(Node * & k3) const;
        void doubleRotateWithRightChild(Node * & k1) const;
        void handleReorient(const Comparable & item );
        RedBlackNode<Comparable> *rotate(const Comparable & item,Node *theParent) const;
    };
    
    template<class Comparable>
    class RedBlackNode
    {
        //为了测试写成public  因为默认是私有的
    public:
    
        Comparable element;
        RedBlackNode *left;
        RedBlackNode *right;
        int color;
        RedBlackNode(const Comparable& theElement=Comparable(),//该类型默认构造的对象
                     RedBlackNode *lt=NULL,
                     RedBlackNode *rt=NULL,
                     int c=RedBlackTree<Comparable>::BLACK)
                     :element(theElement),left(lt),right(rt),color(c){}
    
    friend class RedBlackTree<Comparable>;
    };
    
    template<class Comparable>
    RedBlackTree<Comparable>::RedBlackTree(const Comparable &negInf)
    {
    
        nullNode=new Node();//空节点
        nullNode->left=nullNode->right=nullNode;
        header=new Node(negInf); //伪头 包含一个负无穷数
        header->left=header->right=nullNode;
    }
    template<class Comparable>
    RedBlackTree<Comparable>::~RedBlackTree()//构造函数
    {
    
        delete nullNode;
        delete header;
    }
    template <class Comparable>
    void RedBlackTree<Comparable>::insert(const Comparable& x)
    {
    
        current=parent=grand=header;
        nullNode->element=x;
    
        while(current->element!=x)
        {
            great=grand;  grand=parent;  parent=current;
            current=x<current->element?current->left:current->right;
            if(current->left->color==RED&&current->right->color==RED)
                handleReorient(x);
        }
        if(current!=nullNode)
    
              throw "had exited";
    
        current=new Node(x,nullNode,nullNode);
        if(x<parent->element)
            parent->left=current;
        else
            parent->right=current;
    
        handleReorient(x);
    
    //自动平衡->红黑树
    
    
    
    
    
    
    }
    
    template<class Comparable>
    void RedBlackTree<Comparable>::rotateWithLeftChild(Node * & k2) const//向右转
    {
       Node *k1=k2->left;
       k2->left=k1->right;
       k1->right=k2;
       k2=k1;
    
    }
    template<class Comparable>
    void RedBlackTree<Comparable>::rotateWithRightChild(Node * & k1) const//向左转
    {
         Node *k2=k1->right;
       k1->right=k2->left;
       k2->left=k1;
       k1=k2;
    
    }
    template<class Comparable>//双旋转
    void RedBlackTree<Comparable>::doubleRotateWithLeftChild(Node * & k3) const
    {
        rotateWithRightChild(k3->left);
        rotateWithLeftChild(k3);
    }
    template<class Comparable>
    void RedBlackTree<Comparable>::doubleRotateWithRightChild(Node * & k1) const
    {
    
        rotateWithLeftChild(k1->right);
        rotateWithRightChild(k1);
    }
    //单旋转:新插入的节点是外部孙子
    //双旋转:新插入的节点是内部孙子
    template<class Comparable>
    void RedBlackTree<Comparable>::handleReorient(const Comparable & item )
    {
        //变色  把有两个红色儿子的父亲变成红的 两个儿子变成黑的
        current->color=RED;
        current->left->color=BLACK;
        current->right->color=BLACK;
    
    
        if(parent->color==RED)
        {
            grand->color=RED;
            if(item<grand->element!=item<parent->element)
            {
                parent=rotate(item,grand);//内部孙子则多旋转一次
            }
            current=rotate(item,great);
            current->color=BLACK;
        }
        header->right->color=BLACK;
        //单旋转
        //双旋转
    
    }
    template<class Comparable>
    RedBlackNode<Comparable> * RedBlackTree<Comparable>::rotate(const Comparable & item,Node *theParent) const
    {
        if(item<theParent->element)
       {
           item<theParent->left->element?
           rotateWithLeftChild(theParent->left):
               rotateWithRightChild(theParent->left);
               return theParent->left;
       }
       else
       {
           item<theParent->right->element?
           rotateWithLeftChild(theParent->right):
               rotateWithRightChild(theParent->right);
               return theParent->right;
       }
    
    }
    
    #endif // PRACTICE1_H_INCLUDED

    practice.cpp

    //c++ map和set是由红黑树实现的
    #include<iostream>
    #include"practice1.h"
    using namespace std;
    
    int main()
    {
    
        const int Neg=-999888;
        RedBlackTree<int> t(Neg);
    //    t.insert(30);
    //    t.insert(15);
    //    t.insert(70);
    //    t.insert(20);
    //    cout<<"ok"<<endl;
    //    cout<<t.header->right->element<<endl;
    //    cout<<t.header->right->left->element<<endl;
    //    cout<<t.header->right->left->right->element<<endl;
    
    
    
    //    cout<<"向右转"<<endl;
    //    t.rotateWithLeftChild(t.header->right);
    //    cout<<t.header->right->element<<endl;
    //    cout<<t.header->right->right->left->element<<endl;
    //    cout<<"向左转"<<endl;
    //    t.rotateWithRightChild(t.header->right);
    //    cout<<t.header->right->element<<endl;
    //    cout<<t.header->right->right->left->element<<endl;
        t.insert(50);
        t.insert(40);
        t.insert(30);
        cout<<""<<t.header->right->element<<endl;
         t.insert(60);
        // cout<<"头"<<t.header->right->left->right->element<<endl;
         t.insert(20);
        // cout<<"头"<<t.header->right->left->left->element<<endl;
         t.insert(35);
         t.insert(31);
         cout<<""<<t.header->right->element<<endl;
    
    //
    //    cout<<t.header->right->left->element<<endl;
    //     cout<<t.header->right->left->left->right->element<<endl;
    //     t.doubleRotateWithLeftChild(t.header->right->left);
    //     cout<<t.header->right->left->element<<endl;//6
    //     cout<<t.header->right->left->left->right->element<<endl;//5
        cout<<""<<t.header->right->element<<endl;
        return 0;
    }
  • 相关阅读:
    odoo 的各种domain
    odoo search之时间搜索,时间段查询
    git 修改远程仓库地址
    Windows 挂起进程
    结构体 偏移量 (size_t)&(((s *)0)->m) , list相关
    Data Flow Diagram with Examples
    Windows环境,获取当前线程的ID,GetCurrentThreadId
    获取 保存 系统信息 [Windows]
    notepad正则删除关键词所在行
    文件或文件夹改变后,发信号让系统刷新
  • 原文地址:https://www.cnblogs.com/libin123/p/10420179.html
Copyright © 2020-2023  润新知