数据结构之二叉树

本文介绍了二叉树的基本概念,包括遍历方法(前序、中序、后序)、完全二叉树、满二叉树及存储方式等,并详细阐述了二叉树的创建、遍历、复制、销毁等操作的实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

二叉树的一些概念这里简单说一下

  1. 二叉树的遍历有三种,前序,中序和后序,前序即按照DLR(结点->左子树->右子树)的顺序遍历,中序则是LDR,后序则是LRD。
  2. 完全二叉树,除了最底层,各层节点数均为最大值,同时最下层的节点集中在左侧,且中间不能有间隔。
  3. 满树即为全满的树。
  4. 树的存储结构:顺序存储和链式存储。顺序存储即从上到下,从左到右依次存放,完全二叉树可用数组,一层一层放,非完全二叉树先用无效的数据将其补充为完全二叉树,然后再用数组,但是会产生冗余。
  5. 有序二叉树,对于树中任意节点,若其左子树非空,则左子树中所有的节点的值都小于或等于该节点的值;若其右子树非空,则右子树中所有节点的值都大于或等于该节点的值。,即左小右大的规则。这样可得中序的遍历,可用于排序。也可用于搜索,收缩搜索的范围。
  6. 时间复杂度:O(logN)。

其他的基本概念这里就不赘述了,下面是编程实现二叉树的一些基本操作。从遍历的逻辑可以看出,二叉树的遍历和递归一模一样,因此,我们的二叉树的操作基本用递归。

树的结构

typedef struct BTree
{
    char data;              //数据
    struct BTree *lChild;   //左孩子
    struct BTree *rChild;   //右孩子
} BinTree;

创建一棵树

BinTree* CreateTree(BinTree *p)
{
    char ch;
    scanf("%c", &ch);
    if(ch == '#')        //代表子节点为空
        return NULL;

    p=(BinTree *)malloc(sizeof(BinTree));
    p->data=ch;
    p->lChild=CreateTree(p->lChild);
    p->rChild=CreateTree(p->rChild);
    return p;
}

销毁树

void BTreeSetNull(BTree *tree)
{
      if(tree==NULL)
      {
          return;
      }
      BTreeSetNull(tree->lChild);
      BTreeSetNull(tree->rChild);
      free(tree);
      tree = NULL;
}

前序遍历

void PreOrder(BinTree *T)
{
    if(T){
        printf("%c", T->data);
        PreOrder(T->lChild);
        PreOrder(T->rChild );
    }
}

中序遍历

void ZhongXu(BinTree *T)
{
    if(T)
    {
        ZhongXu(T->lChild);
        printf("%c", T->data);
        ZhongXu(T->rChild);
    }
}

后序遍历

void HouXu(BinTree *T)
{
    if(T)
    {
        HouXu(T->lChild);
        HouXu(T->rChild );
        printf("%c", T->data);
    }
}

树的深度

int Depth(BinTree *T)
{
    int dep=0, dep1, depr;
    if(!T) dep=0;
    else{
        dep1=Depth(T->lChild);
        depr=Depth(T->rChild );
        dep=1+(dep1>depr?dep1:depr);
    }
    return dep;
}

复制树

BinTree* copybtree(BinTree* root)
{
    BinTree* newnode;
    if(root == NULL)
    {
        return NULL;
    }
    else
    {
        newnode = (BinTree*)malloc(sizeof(BinTree));
        newnode->data = root->data;
        newnode->lChild = copybtree(root->lChild);
        newnode->rChild = copybtree(root->rChild);
        return newnode;
    }
}

求树的叶子数

int Sumleaf(BinTree *T)
{
    int sum=0;
    int m = 0;
    int n = 0;

    if(T)
    {
        if((!T->lChild) && (!T->rChild))
            sum++;

        m = Sumleaf(T->lChild);
        sum += m;

        n = Sumleaf(T->rChild );
        sum += n;
    }
    return sum;
}

测试用例这里就不写了,要注意的是我们的输入必须按照树的前序,因为第一个节点一定为树的根节点。

这里举一个例子:

这里写图片描述

二叉树的操作就到这里。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值