二叉树的简单实现

本篇博文主要关注C++数据结构二叉树的简单实现,主要实现二叉树类的构建,包括二叉树的构造、拷贝构造、析构函数、赋值运算符的重载、前序中序后序层序遍历二叉树、查找指定节点、查找节点的总个数等功能函数,主要依靠递归算法完成。
 树的结点类型主要是根结点,指向右孩子的指针和指向左孩子的指针。下面是结点的构造函数:
 struct BinaryTreeNode

{
BinaryTreeNode* _left;
BinaryTreeNode* _right;
T _data;
BinaryTreeNode(const T& x)
:_left(NULL)
, _right(NULL)
, _data(x)
{}
};`
下面可以直接进行二叉树类:

template <class T>
class BinaryTree
{
    typedef BinaryTreeNode<T> Node;
public:
    BinaryTree()
        :_root(NULL)
    {}


    BinaryTree(T* a, size_t size, const T& invalid)
    {
        size_t index = 0;
        _root = MakeBinaryTree(a, size, invalid,index);
    }
    BinaryTree(const BinaryTree<T>&t)
    {
        _root = CopyTree(t._root);
    }
    ~BinaryTree()
    {
        Destroy(_root);
    }
    BinaryTree<T>& operator=(BinaryTree<T> t)
    {
        if (this != &t)
        {
            std::swap(_root, t._root);
        }
        return *this;
    }
    protected:
    Node* MakeBinaryTree(T* a,size_t size,const T& invalid,size_t & index)
    {
        Node* root = NULL;
        if (index < size && a[index] != invalid)
        {
            root = new Node(invalid);
                root->_data= a[index];
                root->_left = MakeBinaryTree(a, size, invalid,++index);
                root->_right = MakeBinaryTree(a, size,invalid,++index);


        }
        return root;
    }
    }

二叉树的前序遍历:根(当前)结点->左结点->右结点;
中序遍历:左结点->根(当前)结点->右结点;
后序遍历:左结点->右结点->根(当前)结点;代码实现:

void _PrevOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        cout << arrot->_data << "";
        _PrevOrde(aroot->_left);
        _PrevOrde(aroot->_right);
    }
    void _InOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        _InOrder(aroot->_left);
        cout << aroot->_data << "";
        _InOrder(aroot->_right);
    }
    void _PostOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        _PostOrder(aroot->_left);
        _PostOrder(aroot->_right);
        cout << aroot->_data << "";
    }

层序遍历:就是一层一层的访问二叉树,利用队列可以实现

void LevelOrder()
    {
        Node* aroot;
        queue<Node*> q;
        q.push(aroot);
        while (!q.empty())
        {
            Node* top = q.front();
            q.pop();
            cout << top->_data << "";
            if (top->_left)
            {
                q.push(top->_left);

            }
            if (top->_right)
            {
                q.push(top->_right);
            }
        }
    }

其余函数相对简单,以下是源码:

#pragma once
#include<iostream>
#include<stdlib.h>
#include<assert.h>
#include<queue>
#include<stack>
using namespace std;
template <typename T>
struct BinaryTreeNode
{
    BinaryTreeNode<T>* _left;
    BinaryTreeNode<T>* _right;
    T _data;
    BinaryTreeNode(const T& x)
        :_left(NULL)
        , _right(NULL)  
        , _data(x)
    {}
};
template <class T>
class BinaryTree
{
    typedef BinaryTreeNode<T> Node;
public:
    BinaryTree()
        :_root(NULL)
    {}


    BinaryTree(T* a, size_t size, const T& invalid)
    {
        size_t index = 0;
        _root = MakeBinaryTree(a, size, invalid,index);
    }
    BinaryTree(const BinaryTree<T>&t)
    {
        _root = CopyTree(t._root);
    }
    ~BinaryTree()
    {
        //Destroy(_root);
    }
    BinaryTree<T>& operator=(BinaryTree<T> t)
    {
        if (this != &t)
        {
            std::swap(_root, t._root);
        }
        return *this;
    }
    void PrevOrder()//前序遍历
    {
        cout << "前序:";
        _PrevOrder(_root);
        cout << endl;

    }
    void InOrder()//中序遍历
    {
        cout << "中序:";
        _InOrder(_root);
        cout << endl;

    }
    void PostOrder()
    {
        cout << "后序:";
        _PostOrder(_root);
        cout << endl;
    }
    void PrevOrder_NonR()
    {
        Node* cur = _root;
        stack<Node*> s;
        if (cur == NULL)
            return;
        while (cur || !s.empty())
        {
            while (cur)
            {
                s.push();
                cout << cur->_data << "";
                cur = cur->_left;
            }
            Node* top = s.top();
            s.pop();
            cur = top->_right;
        }
        cout << endl;
    }
    void InOrdere_NonR()
    {
        Node* cur = _root;
        stack<Node*>s;
        if (cur == NULL)
            rerurn;
        while (cur || !s.empty())
        {
            while (cur)
            {
                s.push();
                cur = cur->_left;
            }
            Node* top = s.top;
            cout << top->_data << "";
            s.pop();
            cur = top->_right;
        }
        cout << endl;

    }
    void PrevOrderNonR()
    {
        Node* cur = _root;
        Node* prev = NULL;
        stack<Node*> s;
        while (cur || s.empty())
        {
            while (cur)
            {
                s.push();
                cur = cur->_left;

            }
            Node* top = s.top();
            if (top->_right == NULL || prev == top->_right)
            {
                cout << top->_data << "";
                prev = top;
                s.pop();
            }
            else
            {
                cur = top->_right;

            }
        }
        cout << endl;

    }
    void LevelOrder()
    {
        Node* aroot;
        queue<Node*> q;
        q.push(aroot);
        while (!q.empty())
        {
            Node* top = q.front();
            q.pop();
            cout << top->_data << "";
            if (top->_left)
            {
                q.push(top->_left);

            }
            if (top->_right)
            {
                q.push(top->_right);
            }
        }
    }
    size_t FindKLeves(size_t k)
    {
        return _FindKLeves(_root, k);
    }

    size_t FindX(const T&x)
    {
        return  _FindX(_root, x);
    }
    size_t Size()
    {
        return _Size(_root);
    }
    size_t Depth()
    {
        return _Depth(_root);
    }
protected:
    Node* _root;
protected:
    Node* MakeBinaryTree(T* a,size_t size,const T& invalid,size_t & index)
    {
        Node* root = NULL;
        if (index < size && a[index] != invalid)
        {
            root = new Node(invalid);
                root->_data= a[index];
                root->_left = MakeBinaryTree(a, size, invalid,++index);
                root->_right = MakeBinaryTree(a, size,invalid,++index);


        }
        return root;
    }
    Node* CopyTree(const BinaryTree<T>* _root)
    {
        if (_root == NULL)
        {
            return;
        }
        Node* root = new Node(_root->_data);
        root->_left = CopyTree(_root->_left);
        root->_right = CopyTree(_root->_right);

        return root;

    }
    void Destroy(Node* root)
    {
        //Node aroot = _root;
        if (root = NULL)
        {
            return;
        }
        Destroy(root->_left);
        Destroy(root->_right);
        delete root;

    }
    void _PrevOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        cout << arrot->_data << "";
        _PrevOrde(aroot->_left);
        _PrevOrde(aroot->_right);
    }
    void _InOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        _InOrder(aroot->_left);
        cout << aroot->_data << "";
        _InOrder(aroot->_right);
    }
    void _PostOrder(Node* _root)
    {
        Node* aroot = _root;
        if (aroot == NULL)
            return;
        _PostOrder(aroot->_left);
        _PostOrder(aroot->_right);
        cout << aroot->_data << "";
    }
    size_t _FindKLeves(Node* _root, size_t k)
    {
        Node* cur = _root;
        if (cur == NULL || k = 0)
            return 0;
        if (k == 1)
        {
            return 1;
        }
        size_t left = _FindKLeves(cur->_left, k - 1);
        size_t right = _FindKLeves(cur->_right, k - 1);
        return left + right;
    }
        Node* _FindX(Node* _root, const T& x)
        {
            Node* ret = NULL;
            Node* cur = _root;
            if (cur == NULL)
                return;
            if (cur->_data == x)
            {
                ret = cur;
            }
            else
            {
                ret = _FindX(cur->_left, x);
                if (ret == NULL)
                {
                    ret = _FindX(cur->_right, x);

                }
            }
            return ret;
        }
        size_t _Size(BinaryTreeNode<T>* _root)
        {
            size_t  ret = 0;
            if (_root == NULL)
                return ret;
            ret++;
            ret += _Size(_root->_left);
            ret += _Size(_root->_right);
        }
        size_t _Depth(Node* _root)
        {
            if (_root == NULL)
                return;
            int left = _Depth(_root->_left) + 1;
            int right = _Depth(_root->_right) + 1;
            return left > right ? left : right;
        }

};

void TestBinaryTree()
{
    int a[20] = { 1, 2, 3, '#', '#', 4, '#', '#', 5, 6 };
    BinaryTree<int> t(a, 10, '#');
    void PrevOrder();//前序遍历,其余测试可以自行添加。

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值