【练习】二叉树的遍历

1.按层遍历

void oper(ChainBinTree *p) //操作二叉树结点数据 
{
     printf("%c ",p->data); //输出数据
     return;
}

void BinTree_Level(ChainBinTree *bt,void (*oper)(ChainBinTree *p)) //按层遍历 
{
     ChainBinTree *p;
     ChainBinTree *q[QUEUE_MAXSIZE]; //定义一个顺序栈 
     int head=0,tail=0;//队首、队尾序号 
     if(bt)//若队首指针不为空     
     {
         tail=(tail+1)%QUEUE_MAXSIZE;//计算循环队列队尾序号 
         q[tail] = bt;//将二叉树根指针进队
     }
     while(head!=tail) //队列不为空,进行循环 
     {
         head=(head+1)%QUEUE_MAXSIZE; //计算循环队列的队首序号 
         p=q[head]; //获取队首元素 
         oper(p);//处理队首元素 
         if(p->left!=NULL) //若结点存在左子树,则左子树指针进队 
         {
             tail=(tail+1)%QUEUE_MAXSIZE;//计算循环队列的队尾序号 
             q[tail]=p->left;//将左子树指针进队 
         }

         if(p->right!=NULL)//若结点存在右孩子,则右孩子结点指针进队 
         {
             tail=(tail+1)%QUEUE_MAXSIZE;//计算循环队列的队尾序号 
             q[tail]=p->right;//将右子树指针进队 
         }
     }
     return; 
}

  在整个队列的处理中,首先从根节点开始,将每层的结点逐步进入队列,这样就可以得到按层遍历的效果。


2.递归遍历二叉树

先序遍历

void BinTree_DLR(ChainBinTree *bt,void (*oper)(ChainBinTree *p))  //先序遍历 
{     
     if(bt)//树不为空,则执行如下操作 
     {
         oper(bt); //处理结点的数据 
         BinTree_DLR(bt->left,oper);
         BinTree_DLR(bt->right,oper);
     }
     return; 
}

中序遍历

void BinTree_LDR(ChainBinTree *bt,void(*oper)(ChainBinTree *p))  //中序遍历 
{
     if(bt)//树不为空,则执行如下操作 
     {
         BinTree_LDR(bt->left,oper); //中序遍历左子树
         oper(bt);//处理结点数据 
         BinTree_LDR(bt->right,oper); //中序遍历右子树/
     }
     return; 
} 

后序遍历

void BinTree_LRD(ChainBinTree *bt,void (*oper)(ChainBinTree *p)) //后序遍历
{
     if(bt)
     {
         BinTree_LRD(bt->left,oper); //后序遍历左子树 
         BinTree_LRD(bt->right,oper); //后序遍历右子树/
         oper(bt); //处理结点数据
     }
     return; 
}

3.非递归遍历二叉树

  利用栈可以实现遍历二叉树的非递归算法。

先序遍历

void PreOrderTraverse2(BiTree T)
/*先序遍历二叉树的非递归实现*/
{
    BiTree stack[MaxSize];              /*定义一个栈,用于存放结点的指针*/
    int top;                            /*定义栈顶指针*/
    BitNode *p;                         /*定义一个结点的指针*/
    top=0;                          /*初始化栈*/
    p=T;
    while(p!=NULL||top>0)
    {
        while(p!=NULL)                  /*如果p不空,访问根结点,遍历左子树*/
        {
            printf("%2c",p->data);          /*访问根结点*/
            stack[top++]=p;                 /*将p入栈*/
            p=p->lchild;                /*遍历左子树*/
        }
        if(top>0)                       /*如果栈不空*/
        {
            p=stack[--top];                 /*栈顶元素出栈*/
            p=p->rchild;                    /*遍历右子树*/
        }
    }
}

中序遍历

void InOrderTraverse2(BiTree T)
/*中序遍历二叉树的非递归实现*/
{
    BiTree stack[MaxSize];              /*定义一个栈,用于存放结点的指针*/
    int top;                            /*定义栈顶指针*/
    BitNode *p;                         /*定义一个结点的指针*/
    top=0;                          /*初始化栈*/
    p=T;
    while(p!=NULL||top>0)
    {
        while(p!=NULL)                  /*如果p不空,访问根结点,遍历左子树*/
        {
            stack[top++]=p;                 /*将p入栈*/
            p=p->lchild;                /*遍历左子树*/
        }
        if(top>0)                       /*如果栈不空*/
        {
            p=stack[--top];                 /*栈顶元素出栈*/
            printf("%2c",p->data);          /*访问根结点*/
            p=p->rchild;                    /*遍历右子树*/
        }
    }
}

后序遍历

void PostOrderTraverse2(BiTree T)
/*后序遍历二叉树的非递归实现*/
{
    BiTree stack[MaxSize];              /*定义一个栈,用于存放结点的指针*/
    int top;                            /*定义栈顶指针*/
    BitNode *p,*q;                      /*定义结点的指针*/
    top=0;                              /*初始化栈*/
    p=T,q=NULL;                         /*初始化结点的指针*/
    while(p!=NULL||top>0)
    {
        while(p!=NULL)                      /*如果p不空,访问根结点,遍历左子树*/
        {
            stack[top++]=p;                 /*将p入栈*/
            p=p->lchild;                    /*遍历左子树*/
        }
        if(top>0)                           /*如果栈不空*/
        {
            p=stack[top-1];                     /*取栈顶元素*/
            if(p->rchild==NULL||p->rchild==q)   /*如果p没有右孩子结点,或右孩子结点已经访问过*/
            {
                printf("%2c",p->data);          /*访问根结点*/
                q=p; 
                p=NULL; 
                top--;      
            }
            else
                p=p->rchild;
        }
    }
}
  • 1
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
(1)非递归定义 树(tree)是由n(n≥0)个结点组成的有限集合。n=0的树称为空树;n>0的树T: ① 有且仅有一个结点n0,它没有前驱结点,只有后继结点。n0称作树的根(root)结点。 ② 除结点外n0 , 其余的每一个结点都有且仅有一个直接前驱结点;有零个或多个直接后继结点。 (2)递归定义 一颗大树分成几个大的分枝,每个大分枝再分成几个小分枝,小分枝再分成更小的分枝,… ,每个分枝也都是一颗树,由此我们可以给出树的递归定义。 树(tree)是由n(n≥0)个结点组成的有限集合。n=0的树称为空树;n>0的树T: ① 有且仅有一个结点n0,它没有前驱结点,只有后继结点。n0称作树的根(root)结点。 ② 除根结点之外的其他结点分为m(m≥0)个互不相交的集合T0,T1,…,Tm-1,其中每个集合Ti(0≤i<m)本身又是一棵树,称为根的子树(subtree)。 2、掌握树的各种术语: (1) 父母、孩子与兄弟结点 (2) 度 (3) 结点层次、树的高度 (4) 边、路径 (5) 无序树、有序树 (6) 森林 3、二叉树的定义 二叉树binary tree)是由n(n≥0)个结点组成的有限集合,此集合或者为空,或者由一个根结点加上两棵分别称为左、右子树的,互不相交的二叉树组成。 二叉树可以为空集,因此根可以有空的左子树或者右子树,亦或者左、右子树皆为空。 4、掌握二叉树的五个性质 5、二叉树的二叉链表存储。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值