• c++实现二叉树层序、前序创建二叉树,递归非递归实现二叉树遍历


    #include <iostream>
    #include <cstdio>
    #include <stdio.h>
    #include <string>
    #include <queue>
    #include <stack>
    using namespace std;
    
    class Node{
    public :
        char data;
        struct Node *lchild,*rchild;
    };
    
    class BiTree{
    public:
        Node * root;//头结点
        int height=0;//树的高度
        BiTree() {root=NULL;}
        //层序创建二叉树
        void create_level(string &s)
        {
           int p=0;
           root=new Node();
    
           Node *t,*i,*j;
           queue<Node*> qTree;//定义一个队列,存储节点
           while(true)
           {
               if(p==s.size())break;
               if(p==0)//当头结点未创建
               {
                   t=new Node();
                   t->data=s[p];
                   qTree.push(t);//头结点进队
                   root=t;
                   p++;
               }
               else
               {
                   t=qTree.front();//该节点出队
                   if(p==s.size())break;//树的构建完毕
                   if(s[p]=='#')//不存在左节点
                   {
                      t->lchild=NULL;
                      p++;
                   }
                   else//存在左节点
                   {
                       i=new Node();
                       i->data=s[p];
                       t->lchild=i;//左节点进队
                       qTree.push(i);
                       p++;
                   }
    
                   if(p==s.size())break;
                   if(s[p]=='#')//不存在右节点
                   {
                      t->rchild=NULL;
                      p++;
                   }
                   else//存在右节点
                   {
                       j=new Node();
                       j->data=s[p];
                       t->rchild=j;
                       qTree.push(j);
                       p++;
                   }
    
                   qTree.pop();//节点左右节点已创建,该节点出队
               }
           }
    
        }
        //前序递归创建二叉树
        void create_pre(string s)
        {
            int p=-1;
            root=create(s,p);
        }
        Node *create(string &s,int &p)
        {
            ++p;
            Node *t;
            if((unsigned)p>=s.size())
            {
                return NULL;
            }
            else
            {
                if(s[p]=='#')
                {
                    t=NULL;
                }
                else
                {
                    t=new Node;
                    t->data=s[p];
                    t->lchild=create(s,p);
                    t->rchild=create(s,p);
                }
                return t;
            }
        }
    
        //前序递归遍历二叉树
        void read_pre_oder(Node *t)
        {
            if(t!=NULL)
            {
                cout<<t->data<<' ';
                read_pre_oder(t->lchild);
                read_pre_oder(t->rchild);
            }
        }
        //中序递归遍历二叉树
        void read_mid_oder(Node *t)
        {
            if(t!=NULL)
            {
                read_mid_oder(t->lchild);
                cout<<t->data<<' ';
                read_mid_oder(t->rchild);
            }
        }
        //后续递归遍历二叉树
        void read_beh_oder(Node *t)
        {
            if(t!=NULL)
            {
                read_beh_oder(t->lchild);
                read_beh_oder(t->rchild);
                cout<<t->data<<' ';
            }
        }
    
        //利用栈实现前序遍历二叉树
        void read_pre_oder_stack(Node *t)
        {
            if(t!=NULL)
            {
                stack<Node*> sTree;//声明一个栈存储节点
                while(true)
                {
                    if(sTree.size()==0&&t==NULL) break;
                    while(true)//一直遍历左节点,输出
                    {
                        if(t==NULL) break;//该节点不存在左节点,跳出循环
                        cout<<t->data<<' ';
                        sTree.push(t);//节点进栈,以便后期遍历右节点
                        t=t->lchild;
                    }
                    t=sTree.top();//查看该节点是否存在右子树
                    sTree.pop();//节点已遍历出栈
                    /*遍历该节点右子树,若不存在右子树,继续循环,
                    存在则进入内部while循环查找该右子树的左节点*/
                    t=t->rchild;
    
                }
            }
        }
        //利用栈实现中序遍历二叉树
        void read_mid_oder_stack(Node *t)
        {
            if(t!=NULL)
            {
                stack<Node*> sTree;//声明一个栈存储节点
                while(true)
                {
                    if(sTree.size()==0&&t==NULL) break;
                    while(true)
                    {
                        if(t==NULL) break;
                        sTree.push(t);//一直存储左节点
                        t=t->lchild;
                    }
                    t=sTree.top();
                    cout<<t->data<<' ';//不存在左节点,输出该节点
                    sTree.pop();//该节点出栈
                    t=t->rchild;//查找该节点的右子树
                }
            }
        }
        //利用栈实现后序遍历二叉树
        void read_beh_oder_stack(Node *t)
        {
            if(t!=NULL)
            {
                stack<Node*> sTree1;//该栈用于存储遍历过程的节点
                stack<Node*> sTree2;//该栈用于存储遍历结果,输出
                sTree1.push(t);//头节点进栈
                while(true)
                {
                    if (sTree1.size()==0) break;
                    t=sTree1.top();
                    sTree1.pop();
                    if(t->lchild!=NULL)//存在左节点,节点进栈
                    {
                        sTree1.push(t->lchild);
                    }
                    if(t->rchild!=NULL)//存在右节点,节点进栈
                    {
                        sTree1.push(t->rchild);
                    }
                    sTree2.push(t);//存储该节点(第一步开始存储的就是头节点,头结点存储在栈底)
                }
                while(true)//输出
                {
                    if(sTree2.size()==0) break;
                    t=sTree2.top();
                    cout<<t->data<<' ';
                    sTree2.pop();
                }
            }
        }
        //利用栈、队列实现层序遍历
        void read_lev_oder_stack(Node *t)
        {
            if(t!=NULL)
            {
                stack<Node*> sTree;
                queue<Node*> qTree;
                sTree.push(t);
                qTree.push(t);
                while(true)
                {
                    if(sTree.size()==0)break;
                    t=sTree.top();
                    sTree.pop();
                    if(t->lchild!=NULL)
                    {
                        sTree.push(t->lchild);
                        qTree.push(t->lchild);
                    }
                    if(t->rchild!=NULL)
                    {
                        sTree.push(t->rchild);
                        qTree.push(t->rchild);
                    }
                }
                while(true)
                {
                    if(qTree.size()==0) break;
                    t=qTree.front();
                    cout<<t->data<<' ';
                    qTree.pop();
                }
            }
        }
    
        //求树的高度
        int tree_height(Node *t)
        {
            get_height(t,0);
            return height;
        }
        void get_height(Node *t,int h)
        {
            if(t==NULL) return;
            h++;
            if(h>height)
            {
                height=h;
            }
            get_height(t->lchild,h);
            get_height(t->rchild,h);
        }
    };
    
    int main()
    {
        BiTree a;
        string s;
        s="ABD##E#F##C##";
    
    //    a.create_level(s);
        a.create_pre(s);
    
        cout<<"递归实现前序遍历"<<endl;
        a.read_pre_oder(a.root);
        cout<<endl<<"递归实现中序遍历"<<endl;
        a.read_mid_oder(a.root);
        cout<<endl<<"递归实现后序遍历"<<endl;
        a.read_beh_oder(a.root);
        cout<<endl;
    
        cout<<"栈实现前序遍历"<<endl;
        a.read_pre_oder_stack(a.root);
        cout<<endl<<"栈实现中序遍历"<<endl;
        a.read_mid_oder_stack(a.root);
        cout<<endl<<"栈实现后序遍历"<<endl;
        a.read_beh_oder_stack(a.root);
        cout<<endl<<"栈、队列实现层序遍历"<<endl;
        a.read_lev_oder_stack(a.root);
        cout<<endl<<"树的高度为: "<<endl;
    
        int height=a.tree_height(a.root);
        cout<<height<<endl;
    
    
        return 0;
    }

    参考地址:https://blog.csdn.net/ajay666/article/details/76736333https://www.cnblogs.com/ybf-yyj/p/8717601.html

  • 相关阅读:
    linux十九压缩解压
    linux第十八dd命令
    【51单片机】数据类型
    【博客园】
    【C++】简介与环境的搭建
    【树莓派】安装TeamViewer
    【树莓派】Makefile的编写
    【cJSON库】cJSON库的使用
    【树莓派】忘记系统用户密码,如何重置密码
    【树莓派】树莓派与PC机通信
  • 原文地址:https://www.cnblogs.com/ybf-yyj/p/9220104.html
Copyright © 2020-2023  润新知