• 数据结构二叉树的遍历


    数据结构二叉树的遍历,给了个二叉树,前序、中序、后序写出来

      1 #include<iostream>
      2 #include<stdio.h>
      3 #include<queue>
      4 #include<stack>
      5 #include<malloc.h>
      6 using namespace std;
      7 
      8 //二叉树结点的描述
      9 typedef struct BiTNode
     10 {
     11     char data;
     12     struct BiTNode *lchild, *rchild;      //左右孩子
     13 }BiTNode,*BiTree;
     14 
     15 //按先序遍历创建二叉树
     16 //BiTree *CreateBiTree()     //返回结点指针类型
     17 //void CreateBiTree(BiTree &root)      //引用类型的参数
     18 void CreateBiTree(BiTNode **root)    //二级指针作为函数参数
     19 {
     20     char ch; //要插入的数据
     21     scanf("
    %c", &ch);
     22     //cin>>ch;
     23     if(ch=='#')
     24         *root = NULL;
     25     else
     26     {
     27         *root = (BiTNode *)malloc(sizeof(BiTNode));
     28         (*root)->data = ch;
     29         printf("请输入%c的左孩子:",ch);
     30         CreateBiTree(&((*root)->lchild));
     31         printf("请输入%c的右孩子:",ch);
     32         CreateBiTree(&((*root)->rchild));
     33     }
     34 }
     35 
     36 //前序遍历的算法程序
     37 void PreOrder(BiTNode *root)
     38 {
     39     if(root==NULL)
     40         return ;
     41     printf("%c ", root->data); //输出数据
     42     PreOrder(root->lchild); //递归调用,前序遍历左子树
     43     PreOrder(root->rchild); //递归调用,前序遍历右子树
     44 }
     45 
     46 //中序遍历的算法程序
     47 void InOrder(BiTNode *root)
     48 {
     49     if(root==NULL)
     50         return ;
     51     InOrder(root->lchild); //递归调用,前序遍历左子树
     52     printf("%c ", root->data); //输出数据
     53     InOrder(root->rchild); //递归调用,前序遍历右子树
     54 }
     55 
     56 //后序遍历的算法程序
     57 void PostOrder(BiTNode *root)
     58 {
     59     if(root==NULL)
     60         return ;
     61     PostOrder(root->lchild);      //递归调用,前序遍历左子树
     62     PostOrder(root->rchild);      //递归调用,前序遍历右子树
     63     printf("%c ", root->data);    //输出数据
     64 }
     65 
     66 /*
     67 二叉树的非递归前序遍历,前序遍历思想:先让根进栈,只要栈不为空,就可以做弹出操作,
     68 每次弹出一个结点,记得把它的左右结点都进栈,记得右子树先进栈,这样可以保证右子树在栈中总处于左子树的下面。
     69 */
     70 void PreOrder_Nonrecursive(BiTree T)     //先序遍历的非递归
     71 {
     72     if(!T)
     73         return ;
     74 
     75     stack<BiTree> s;
     76     s.push(T);
     77 
     78     while(!s.empty())
     79     {
     80         BiTree temp = s.top();
     81         cout<<temp->data<<" ";
     82         s.pop();
     83         if(temp->rchild)
     84             s.push(temp->rchild);
     85         if(temp->lchild)
     86             s.push(temp->lchild);
     87     }
     88 }
     89 
     90 void PreOrder_Nonrecursive1(BiTree T)     //先序遍历的非递归
     91 {
     92     if(!T)
     93         return ;
     94     stack<BiTree> s;
     95     BiTree curr = T;
     96     while(curr != NULL || !s.empty())
     97     {
     98         while(curr != NULL)
     99         {
    100             cout<<curr->data<<"  ";
    101             s.push(curr);
    102             curr = curr->lchild;
    103         }
    104         if(!s.empty())
    105         {
    106             curr = s.top();
    107             s.pop();
    108             curr = curr->rchild;
    109         }
    110     }
    111 }
    112 
    113 void PreOrder_Nonrecursive2(BiTree T)     //先序遍历的非递归
    114 {
    115     if(!T)
    116         return ;
    117 
    118     stack<BiTree> s;
    119     while(T)          // 左子树上的节点全部压入到栈中
    120     {
    121         s.push(T);
    122         cout<<T->data<<"  ";
    123         T = T->lchild;
    124     }
    125 
    126     while(!s.empty())
    127     {
    128         BiTree temp = s.top()->rchild;  // 栈顶元素的右子树
    129         s.pop();                        // 弹出栈顶元素
    130         while(temp)          // 栈顶元素存在右子树,则对右子树同样遍历到最下方
    131         {
    132             cout<<temp->data<<"  ";
    133             s.push(temp);
    134             temp = temp->lchild;
    135         }
    136     }
    137 }
    138 
    139 void InOrderTraverse1(BiTree T)   // 中序遍历的非递归
    140 {
    141     if(!T)
    142         return ;
    143     BiTree curr = T;    // 指向当前要检查的节点
    144     stack<BiTree> s;
    145     while(curr != NULL || !s.empty())
    146     {
    147         while(curr != NULL)
    148         {
    149             s.push(curr);
    150             curr = curr->lchild;
    151         }//while
    152         if(!s.empty())
    153         {
    154             curr = s.top();
    155             s.pop();
    156             cout<<curr->data<<"  ";
    157             curr = curr->rchild;
    158         }
    159     }
    160 }
    161 
    162 void InOrderTraverse(BiTree T)   // 中序遍历的非递归
    163 {
    164     if(!T)
    165         return ;
    166     stack<BiTree> s;
    167     BiTree curr = T->lchild;    // 指向当前要检查的节点
    168     s.push(T);
    169     while(curr != NULL || !s.empty())
    170     {
    171         while(curr != NULL)    // 一直向左走
    172         {
    173             s.push(curr);
    174             curr = curr->lchild;
    175         }
    176         curr = s.top();
    177         s.pop();
    178         cout<<curr->data<<"  ";
    179         curr = curr->rchild;
    180     }
    181 }
    182 
    183 void PostOrder_Nonrecursive1(BiTree T)  // 后序遍历的非递归
    184 {
    185     stack<BiTree> S;
    186     BiTree curr = T ;           // 指向当前要检查的节点
    187     BiTree previsited = NULL;    // 指向前一个被访问的节点
    188     while(curr != NULL || !S.empty())  // 栈空时结束
    189     {
    190         while(curr != NULL)            // 一直向左走直到为空
    191         {
    192             S.push(curr);
    193             curr = curr->lchild;
    194         }
    195         curr = S.top();
    196         // 当前节点的右孩子如果为空或者已经被访问,则访问当前节点
    197         if(curr->rchild == NULL || curr->rchild == previsited)
    198         {
    199             cout<<curr->data<<"  ";
    200             previsited = curr;
    201             S.pop();
    202             curr = NULL;
    203         }
    204         else
    205             curr = curr->rchild;      // 否则访问右孩子
    206     }
    207 }
    208 
    209 void PostOrder_Nonrecursive(BiTree T)  // 后序遍历的非递归     双栈法
    210 {
    211     stack<BiTree> s1 , s2;
    212     BiTree curr ;           // 指向当前要检查的节点
    213     s1.push(T);
    214     while(!s1.empty())  // 栈空时结束
    215     {
    216         curr = s1.top();
    217         s1.pop();
    218         s2.push(curr);
    219         if(curr->lchild)
    220             s1.push(curr->lchild);
    221         if(curr->rchild)
    222             s1.push(curr->rchild);
    223     }
    224     while(!s2.empty())
    225     {
    226         printf("%c ", s2.top()->data);
    227         s2.pop();
    228     }
    229 }
    230 
    231 
    232 int visit(BiTree T)
    233 {
    234     if(T)
    235     {
    236         printf("%c ",T->data);
    237         return 1;
    238     }
    239     else
    240         return 0;
    241 }
    242 
    243 void LeverTraverse(BiTree T)   //方法一、非递归层次遍历二叉树
    244 {
    245     queue <BiTree> Q;
    246     BiTree p;
    247     p = T;
    248     if(visit(p)==1)
    249         Q.push(p);
    250     while(!Q.empty())
    251     {
    252         p = Q.front();
    253         Q.pop( );
    254         if(visit(p->lchild) == 1)
    255             Q.push(p->lchild);
    256         if(visit(p->rchild) == 1)
    257             Q.push(p->rchild);
    258     }
    259 }
    260 void LevelOrder(BiTree BT)     //方法二、非递归层次遍历二叉树
    261 {
    262     BiTNode *queue[10];//定义队列有十个空间
    263     if (BT==NULL)
    264         return;
    265     int front,rear;
    266     front=rear=0;
    267     queue[rear++]=BT;
    268     while(front!=rear)//如果队尾指针不等于对头指针时
    269     {
    270         cout<<queue[front]->data<<"  ";  //输出遍历结果
    271         if(queue[front]->lchild!=NULL)  //将队首结点的左孩子指针入队列
    272         {
    273             queue[rear]=queue[front]->lchild;
    274             rear++;    //队尾指针后移一位
    275         }
    276         if(queue[front]->rchild!=NULL)
    277         {
    278             queue[rear]=queue[front]->rchild;    //将队首结点的右孩子指针入队列
    279             rear++;   //队尾指针后移一位
    280         }
    281         front++;    //对头指针后移一位
    282     }
    283 }
    284 
    285 int depth(BiTNode *T)   //树的深度
    286 {
    287     if(!T)
    288         return 0;
    289     int d1,d2;
    290     d1=depth(T->lchild);
    291     d2=depth(T->rchild);
    292     return (d1>d2?d1:d2)+1;
    293     //return (depth(T->lchild)>depth(T->rchild)?depth(T->lchild):depth(T->rchild))+1;
    294 }
    295 int CountNode(BiTNode *T)
    296 {
    297     if(T == NULL)
    298         return 0;
    299     return 1+CountNode(T->lchild)+CountNode(T->rchild);
    300 }
    301 
    302 int main(void)
    303 {
    304     BiTNode *root=NULL; //定义一个根结点
    305     int flag=1,k;
    306     printf("                     本程序实现二叉树的基本操作。
    ");
    307     printf("可以进行建立二叉树,递归先序、中序、后序遍历,非递归先序、中序遍历及非递归层序遍历等操作。
    ");
    308 
    309     while(flag)
    310     {
    311         printf("
    ");
    312         printf("|--------------------------------------------------------------|
    ");
    313         printf("|                    二叉树的基本操作如下:                     |
    ");
    314         printf("|                        0.创建二叉树                          |
    ");
    315         printf("|                        1.递归先序遍历                        |
    ");
    316         printf("|                        2.递归中序遍历                        |
    ");
    317         printf("|                        3.递归后序遍历                        |
    ");
    318         printf("|                        4.非递归先序遍历                      |
    ");
    319         printf("|                        5.非递归中序遍历                      |
    ");
    320         printf("|                        6.非递归后序遍历                      |
    ");
    321         printf("|                        7.非递归层序遍历                      |
    ");
    322         printf("|                        8.二叉树的深度                        |
    ");
    323         printf("|                        9.二叉树的结点个数                    |
    ");
    324         printf("|                        10.退出程序                            |
    ");
    325         printf("|--------------------------------------------------------------|
    ");
    326         printf("                        请选择功能:");
    327         scanf("%d",&k);
    328         switch(k)
    329         {
    330         case 0:
    331             printf("请建立二叉树并输入二叉树的根节点:");
    332             CreateBiTree(&root);
    333             break;
    334         case 1:
    335             if(root)
    336             {
    337                 printf("递归先序遍历二叉树的结果为:");
    338                 PreOrder(root);
    339                 printf("
    ");
    340             }
    341             else
    342                 printf("          二叉树为空!
    ");
    343             break;
    344         case 2:
    345             if(root)
    346             {
    347                 printf("递归中序遍历二叉树的结果为:");
    348                 InOrder(root);
    349                 printf("
    ");
    350             }
    351             else
    352                 printf("          二叉树为空!
    ");
    353             break;
    354         case 3:
    355             if(root)
    356             {
    357                 printf("递归后序遍历二叉树的结果为:");
    358                 PostOrder(root);
    359                 printf("
    ");
    360             }
    361             else
    362                 printf("          二叉树为空!
    ");
    363             break;
    364         case 4:
    365             if(root)
    366             {
    367                 printf("非递归先序遍历二叉树:");
    368                 PreOrder_Nonrecursive1(root);
    369                 printf("
    ");
    370             }
    371             else
    372                 printf("          二叉树为空!
    ");
    373             break;
    374         case 5:
    375             if(root)
    376             {
    377                 printf("非递归中序遍历二叉树:");
    378                 InOrderTraverse1(root);
    379                 printf("
    ");
    380             }
    381             else
    382                 printf("          二叉树为空!
    ");
    383             break;
    384         case 6:
    385             if(root)
    386             {
    387                 printf("非递归后序遍历二叉树:");
    388                 PostOrder_Nonrecursive(root);
    389                 printf("
    ");
    390             }
    391             else
    392                 printf("          二叉树为空!
    ");
    393             break;
    394         case 7:
    395             if(root)
    396             {
    397                 printf("非递归层序遍历二叉树:");
    398                 //LeverTraverse(root);
    399                 LevelOrder(root);
    400                 printf("
    ");
    401             }
    402             else
    403                 printf("          二叉树为空!
    ");
    404             break;
    405         case 8:
    406             if(root)
    407                 printf("这棵二叉树的深度为:%d
    ",depth(root));
    408             else
    409                 printf("          二叉树为空!
    ");
    410             break;
    411         case 9:
    412             if(root)
    413                 printf("这棵二叉树的结点个数为:%d
    ",CountNode(root));
    414             else
    415                 printf("          二叉树为空!
    ");
    416             break;
    417         default:
    418             flag=0;
    419             printf("程序运行结束,按任意键退出!
    ");
    420         }
    421     }
    422     system("pause");
    423     return 0;
    424 }
  • 相关阅读:
    博客园用户体验
    代码大全阅读笔记(三)
    风险评估计划
    课堂练习:给定一个十进制的正整数,写下从1开始,到N的所有整数,然后数一下其中出现“1”的个数。
    代码大全阅读笔记(二)
    “找水王”问题续
    结对开发-- 一维数组求和最大的子数组 (大数溢出)
    结对开发2-二维数组子矩阵和最大值
    电梯调度--初
    梦断代码--阅读笔记2
  • 原文地址:https://www.cnblogs.com/huangxingkezhan/p/3354617.html
Copyright © 2020-2023  润新知