C++数据结构 之 二叉搜索树_Binary Search Tree

来源:互联网 发布:mac输入法 编辑:程序博客网 时间:2024/06/05 21:17

C++数据结构 之 二叉搜索树_Binary Search Tree

源代码只包含头文件

注:需要C++11的支持

一、二叉搜索树

顾名思义,二叉搜索树是建立在二叉树的基础上。但具有如下性质:
(1)若左子树不空,则左子树上所有结点的值均小于它的根结点的值;
(2)若右子树不空,则右子树上所有结点的值均大于它的根结点的值;
(3)左、右子树也分别为二叉搜索树;
(4)没有键值(key)相等的结点。

二叉搜索树

支持的操作:
1、insert 插入元素
2、delete 删除元素
3、search 搜索元素
4、Inorder_Tree_Walk 中序遍历;Preorder_Tree_Walk 先序遍历;Postorder_Tree_Walk 后序遍历
5、Tree_Maximum、Tree_Minimum 基于键值(key)的最大最小值
5、Tree_Successor、Tree_Predecessor基于键值(key)的前驱后继

源代码:

#ifndef BIANRY_SEARCH_TREE_H#define BIANRY_SEARCH_TREE_H#include <memory>#include <utility>#include <stdexcept>#include <functional>using std::shared_ptr;using std::pair;template<typename T>class BST { public:    struct Node{        Node() = default;        Node(const pair<size_t, T> &d, const shared_ptr<Node> &l, const shared_ptr<Node> &r, const shared_ptr<Node> &p) :            data(d), left(l), right(r), parent(p) {}        pair<size_t, T> data;        shared_ptr<Node> left = nullptr;        shared_ptr<Node> right = nullptr;        shared_ptr<Node> parent = nullptr;    };    shared_ptr<Node> Root = nullptr;public:    BST() = default;    ~BST() = default;    size_t Hash_Val(const T &x) {        return std::hash<T>()(x);    }    void Inorder_Tree_Walk(const shared_ptr<Node> &p) {        if (p != nullptr) {            Inorder_Tree_Walk(p->left);            cout << p->data.second << " ";            Inorder_Tree_Walk(p->right);        }    }    void Inorder_Tree_Walk() {        auto p = Root;        if (p != nullptr) {            Inorder_Tree_Walk(p->left);            cout << p->data.second << " ";            Inorder_Tree_Walk(p->right);        }    }    void Preorder_Tree_Walk(const shared_ptr<Node> &p) {        if (p != nullptr) {            cout << p->data.second << " ";            Preorder_Tree_Walk(p->left);            Preorder_Tree_Walk(p->right);        }    }    void Preorder_Tree_Walk() {        auto p = Root;        if (p != nullptr) {            cout << p->data.second << " ";            Preorder_Tree_Walk(p->left);            Preorder_Tree_Walk(p->right);        }    }    void Postorder_Tree_Walk(const shared_ptr<Node> &p) {        if (p != nullptr) {            Postorder_Tree_Walk(p->left);            Postorder_Tree_Walk(p->right);            cout << p->data.second << " ";        }    }    void Postorder_Tree_Walk() {        auto p = Root;        if (p != nullptr) {            Postorder_Tree_Walk(p->left);            Postorder_Tree_Walk(p->right);            cout << p->data.second << " ";        }    }    shared_ptr<Node> Search(const T &x) {        auto temp = Hash_Val(x);        auto p = Root;        while (p != nullptr && temp != p->data.first) {            if (temp < p->data.first) {                p = p->left;            }            else {                p = p->right;            }        }        try {            if (p == nullptr) {                throw std::runtime_error("The element was not found.");            }        }        catch (runtime_error err) {            cout << err.what() << endl;        }        return p;    }    shared_ptr<Node> Tree_Maximum() {        auto p = Root;        while (p->right != nullptr) {            p = p->right;        }        return p;    }    shared_ptr<Node> Tree_Minimum() {        auto p = Root;        while (p->left != nullptr) {            p = p->left;        }        return p;    }    shared_ptr<Node> Tree_Successor(const T &x) {        auto p = Search(x);        if (p->right != nullptr) {            return Tree_Successor(p->right->data.second);        }        auto y = p->parent;        while (y != nullptr && p == y->right) {            p = y;            y = y->parent;        }        return y;    }    shared_ptr<Node> Tree_Predecessor(const T &x) {        auto p = Search(x);        if (p->left != nullptr) {            return Tree_Predecessor(p->left->data.second);        }        auto y = p->parent;        while (y != nullptr && p == y->left) {            p = y;            y = y->parent;        }        return y;    }    void Transplant(const shared_ptr<Node> &p1, const shared_ptr<Node> &P2) {        if (p1->parent == nullptr) {            Root = P2;        }        else if (p1 == p1->parent->left) {            p1->parent->left = P2;        }        else {            p1->parent->right = P2;        }        if (P2 != nullptr) {            P2->parent == p1->parent;        }    }    void Insert(const T &x) {        auto temp = Hash_Val(x);        shared_ptr<Node> New = std::make_shared<Node>(std::make_pair(temp, x), nullptr, nullptr, nullptr);        shared_ptr<Node> Py = nullptr;        auto Px = Root;        while (Px != nullptr) {            Py = Px;            if (temp < Px->data.first) {                Px = Px->left;            }            else {                Px = Px->right;            }        }        New->parent = Py;        if (Py == nullptr) {            Root = New;        }        else if (temp < Py->data.first) {            Py->left = New;        }        else {            Py->right = New;        }    }    void Delete(const T &x) {        auto p = Search(x);        if (p != nullptr) {            if (p->left == nullptr) {                Transplant(p, p->right);            }            else if (p->right == nullptr) {                Transplant(p, p->left);            }            else {                auto Py = Tree_Successor(p->right->data.second);                if (Py->parent != p) {                    Transplant(Py, Py->right);                    Py->right = p->right;                    Py->right->parent = Py;                }                Transplant(p, Py);                Py->left = p->left;                Py->left->parent = Py;            }        }    }    size_t Tree_Hight(const shared_ptr<Node> &p) {        if (p != nullptr) {            size_t left = Tree_Hight(p->left);            size_t right = Tree_Hight(p->right);            if (left > right) {                return left + 1;            }            else {                return right + 1;            }        }        else {            return 0;        }    }    size_t Tree_Hight() {        return Tree_Hight(Root);    }};#endif // !BIANRY_SEARCH_TREE_H

注:每个节点中的元素是一个pair,其中包含键值和卫星数据,键值是基于卫星数据计算出的hash值。

0 0