5.2 二叉树的概念与存储

二叉树的定义与五种形态,满二叉树、完全二叉树等特殊二叉树,二叉树的性质,以及顺序与链式存储。

考查要求 ★★★ 重点掌握 n0 = n2 + 1完全二叉树编号满二叉树二叉链表空指针数

二叉树的定义

二叉树也以递归的形式定义:二叉树是 nn(n≥0n \ge 0)个结点的有限集合,或者为空二叉树;或者由一个根结点和两个互不相交的、被称为根的左子树和右子树组成,左子树和右子树又分别是一棵二叉树。

二叉树有五种基本形态:

∅空二叉树只有根结点只有左子树只有右子树左右子树都有

几种特殊的二叉树

1245367
满二叉树
124536
完全二叉树
12437
非完全二叉树
  1. 满二叉树:一棵高度为 hh,且有 2h−12^h - 1 个结点的二叉树,即树中的每层都含有最多的结点。满二叉树的叶结点都集中在二叉树的最下一层,并且除叶结点之外的每个结点度数均为 2。
  2. 完全二叉树:高度为 hh、有 nn 个结点的二叉树,当且仅当其每个结点都与高度为 hh 的满二叉树中编号为 1∼n1 \sim n 的结点一一对应时,称为完全二叉树。
  3. 二叉排序树:左子树上所有结点的关键字均小于根结点的关键字;右子树上所有结点的关键字均大于根结点的关键字;左右子树又各是一棵二叉排序树(见第 7 章)。
  4. 平衡二叉树:树上任意一个结点的左子树和右子树的深度之差不超过 1(见第 7 章)。
  5. 正则二叉树:树中每个分支结点都有 2 个孩子,即树中只有度为 0 或 2 的结点。

完全二叉树的特点

对满二叉树按层序编号:从根结点起(编号为 1),自上而下、自左向右。完全二叉树有如下特点:

  • 若 i≤⌊n/2⌋i \le \lfloor n/2 \rfloor,则结点 ii 为分支结点,否则为叶结点;
  • 叶结点只可能在层次最大的两层上出现,且最大层次中的叶结点都依次排列在该层最左边的位置上;
  • 若有度为 1 的结点,则只可能有一个,且该结点只有左孩子而无右孩子;
  • 按层序编号后,一旦出现某结点(编号为 ii)为叶结点或只有左孩子,则编号大于 ii 的结点均为叶结点;
  • 若 nn 为奇数,则每个分支结点都有左孩子和右孩子;若 nn 为偶数,则编号最大的分支结点(编号为 n/2n/2)只有左孩子,没有右孩子。

拖动滑块改变结点数,点击任意结点观察编号规律:

交互演示完全二叉树的编号规律——点击结点
123456789101112顺序存储(下标从 1 开始,0 号单元不用)123456789101112123456789101112
结点 i双亲 ⌊i/2⌋孩子 2i、2i+1叶结点
结点 i = 3
  • 双亲:⌊3/2⌋ = 1
  • 左孩子:2×3 = 6
  • 右孩子:2×3+1 = 7
  • 所在层次:⌊log₂3⌋ + 1 = 2
  • i ≤ ⌊n/2⌋ = 6,是分支结点
整棵树(n = 12)
  • 高度 h = ⌈log₂(n+1)⌉ = 4
  • 叶子数 n₀ = ⌈n/2⌉ = 6
  • 度为 1 的结点 n₁ = 1(n 为偶数)
  • 度为 2 的结点 n₂ = n₀ − 1 = 5

二叉树的性质

性质 1 的证明:设度为 0、1、2 的结点个数分别为 n0,n1,n2n_0, n_1, n_2,结点总数 n=n0+n1+n2n = n_0 + n_1 + n_2。再看分支数:除根结点外,其余结点都有一个分支进入,设 BB 为分支总数,则 n=B+1n = B + 1;而这些分支是由度为 1 或 2 的结点射出的,所以 B=n1+2n2B = n_1 + 2n_2。于是 n0+n1+n2=n1+2n2+1n_0 + n_1 + n_2 = n_1 + 2n_2 + 1,即 n0=n2+1n_0 = n_2 + 1。

二叉树的存储结构

顺序存储

用一组地址连续的存储单元依次自上而下、自左至右存储完全二叉树上的结点元素,即将完全二叉树上编号为 ii 的结点元素存储在一维数组下标为 i−1i - 1(或 ii,若 0 号单元不用)的分量中。

  • 完全二叉树和满二叉树采用顺序存储比较合适,既能最大可能地节省存储空间,又能利用数组元素的下标值确定结点在二叉树中的位置以及结点之间的关系。
  • 对于一般的二叉树,为了让数组下标能反映结点之间的逻辑关系,只能添加一些并不存在的空结点。在最坏情况下,一个高度为 hh 且只有 hh 个结点的单支树却需要占据近 2h−12^h - 1 个存储单元。
012345678910111213ABCDEF
一般二叉树 A(B(D,), C(E(,F),)) 的顺序存储(0 号单元不用):为保持下标关系,需要补充大量空结点

链式存储

由于顺序存储的空间利用率较低,因此二叉树一般都采用链式存储结构。二叉链表至少包含 3 个域:数据域 data、左指针域 lchild 和右指针域 rchild。

typedef struct BiTNode {
    ElemType data;                       // 数据域
    struct BiTNode *lchild, *rchild;     // 左、右孩子指针
} BiTNode, *BiTree;

即时练习

即时练习5 题
点击选项即可作答
  1. 1
    已知一棵完全二叉树的第 6 层(设根为第 1 层)有 8 个叶结点,则该完全二叉树的结点个数最多是( )。
  2. 2
    若一棵二叉树有 126 个结点,在第 7 层(根结点在第 1 层)至多有( )个结点。
  3. 3
    一棵完全二叉树上有 1001 个结点,其中叶结点的个数是( )。
  4. 4
    设二叉树有 2n 个结点,且 m < n,则不可能存在( )的结点。
  5. 5
    在含有 n 个结点的二叉链表中,空指针的数目为( )。
学完了吗?

标记完成后,侧栏会显示进度。进度仅保存在本浏览器中。