数据结构之二叉树的遍历


Keep up with the previous article.

链式存储结构

在链式存储结构中我们能更形象地,且更易于理解的描绘二叉树。由二叉树的定义可知,二叉树的结点由一个数据元素和分别指向其左子树和右子树的两个分支构成,则表示二叉树的链表中的结点至少包含3个域:数据域和左右指针域。有时呢,为了便于查找,还可以加一个指向其双亲的指针域。利用这两种结点结构所得二叉树的存储结构分别称之为二叉链表和三叉链表。

容易证得,在含有n个结点的二叉链表有n+1个空链域。由此我们可初始化一下二叉链表:

//  Status是函数的类型,其值是函数结果状态代码
typedef int Status;

//  TElemType是数据元素的类型
typedef char TElemType;

typedef struct BiTNode{
    TElemType data;
    struct BiTNode *lchild,*rchild;     //左右孩子指针
}BiTNode,*BiTree;

Status CreateBiTree(BiTree *T)
{
    //按先序次序输入二叉树中结点的值,空格表空
    char val;
    scanf("%c",&val);
    getchar();                  //清个缓存
    if(val==' ') *T=NULL;
    else{
        if(!(*T=(BiTNode *)malloc(sizeof(BiTNode))))    exit(OVERFLOW);
        (*T)->data=val;
        CreateBiTree(&(*T)->lchild);
        CreateBiTree(&(*T)->rchild);
    }
    return OK;
}

这里采用的是先序遍历的方式插入各结点,该方式简单,易于理解。

遍历二叉树

遍历对线性结构来说是一个很简单的事,但对于二叉树则不然。因其是非线性结构,每个结点都可能有两颗子树,因而需要寻找一种规律,以便使二叉树上的结点能排列在一个线性队列上,从而便于遍历。

假如以L、D、R分别表示遍历左子树、访问根结点和遍历右子树,则可能有6种遍历二叉树的方案。若限定先左后右,则只有3种情况——DLR,LDR,LRD。再基于二叉树的递归定义,可得下述遍历二叉树的递归算法定义。

先序遍历-DLR

若二叉树为空,则空操作,否则:

  1. 访问根结点
  2. 遍历左子树
  3. 遍历右子树

具体算法如下:

Status PreOrderTraverse(BiTree T)
{
    if(T){
        if(VistBiTree(T->data))
            if(PreOrderTraverse(T->lchild))
                if(PreOrderTraverse(T->rchild)) return OK;
        return ERROR;
    }else return OK;
}
中序遍历-LDR

若二叉树为空,则空操作,否则:

  1. 遍历左子树
  2. 访问根结点
  3. 遍历右子树

具体算法如下:

Status InOrderTraverse(BiTree T)
{
    if(T){
        if(InOrderTraverse(T->lchild))
            if(VistBiTree(T->data))
                if(InOrderTraverse(T->rchild)) return OK;
        return ERROR;
    }else return OK;
}
后序遍历-LRD

若二叉树为空,则空操作,否则:

  1. 遍历左子树
  2. 遍历右子树
  3. 访问根结点

具体算法如下:

Status PostOrderTraverse(BiTree T)
{
    if(T){
        if(PostOrderTraverse(T->lchild))
            if(PostOrderTraverse(T->rchild))
                if(VistBiTree(T->data)) return OK;
        return ERROR;
    }else return OK;
}

以上的 VistBiTree函数,即访问结点的data值,需自己建立。


传送门: http://adolesce.cn/archives/20.html

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值