【数据结构】树的定义、树的存储结构

简介: 【数据结构】树的定义、树的存储结构

前言


提到存储结构,可以很自然的想到顺序存储结构和链式存储结构两种。


之前介绍的所有的数据结构都是线性存储结构。本章所介绍的树结构是一种非线性存储结构,存储的是具有“一对多”关系的数据元素的集合。


cb46133043df4ca6b5588c4dec725e71.png


图 1(A) 是使用树结构存储的集合 {A,B,C,D,E,F,G,H,I,J,K,L,M} 的示意图。对于数据 A 来说,和数据 B、C、D 有关系;对于数据 B 来说,和 E、F 有关系。这就是“一对多”的关系。

将具有“一对多”关系的集合中的数据元素按照图 1(A)的形式进行存储,整个存储形状在逻辑结构上看,类似于实际生活中倒着的树(图 1(B)倒过来),所以称这种存储结构为“树型”存储结构。

💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙


🐋树的定义


🌲树的定义


       树(Tree)是 n(n>=0)个结点的有限集。n=0时称为空树。在任意一颗非空树中:


有且仅有一个特定的称为根(root)的结点;

当n>1时,其余结点可分为m(m>0)个互补交互的有限集T1、T2...Tm,其中每一个集合本身又是一棵树,并称为根的子树(SubTree)。


df38fd9b66bb44cbbc3b801a683fe0b7.png


🌲树的特点


n>0时,根节点是唯一的,不可能存在多个根节点。数据结构中的树只有一个根节点。

m>0时,子树的个数没有限制,但他们一定是互不相交的。


🌲结点的分类


结点:树的结点包含一个数据元素和若干指向其子树的分支。

结点的度(Degree):结点拥有的子树。

叶子结点(Leaf)/终端结点:度为0的结点。

分支结点/非终端结点:度不为0的结点。

内部结点:除根节点以外,分支结点也称为内部结点。

树的度:树内各结点的度的最大值。


febfdc26e5fe4082a3f24394ae2a8797.png


🌲结点之间的关系


孩子(Child)和双亲(Parent):结点的子树的根,相应的,该结点称为孩子的双亲。(注意是双亲,不是单亲)


兄弟(sibling):同一个双亲的孩子之间互称兄弟。


结点的祖先:从根结点到该结点所经过分支上的所有结点。


子孙:以某结点为根的子树中的任一结点都称为该节点的子孙。


无序树和有序树:如果将树中结点的各子树看成从左至右是有次序的,不能互换的,则称该数为有序树,否则为无序树。


森林(fores):m(m>=0)棵互不相较的树的集合。


💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙💚❤️💙


🐋树的存储结构


树的4种链式存放方式:

双亲链表存储结构

孩子链表存储结构

双亲孩子链表存储结构

孩子兄弟链表存储结构

b11533763d234947aca101037dec8b41.png


⚡双亲链表存储结构


以一组地址连续的存储单元存放树中的各个结点,每个结点有两个域:


数据域:用于存放树中该结点的值。


指针域:用于存放该结点的双亲结点在存储结构中的位置。


data(数据域) parent(指针域)

存储结点的数据信息 存储该结点的双亲所在数组中的下标

662ace49b4234d0d87fa981e5ed364b6.png


优点:查找一个指定结点的双亲结点非常容易。


缺点:查找指定结点的孩子结点,需要扫描整个链表。


⚡孩子链表存储结构


以一组地址连续的存储单元来存放树中的各个结点,每一个结点有两个域。


数据域:存放该结点的值


指针域:用于存放该结点的孩子链表的头指针。


孩子链表的孩子结点:


child(数据域) next(指针域)


存储某个结点在表头数组中的下标 存储指向某结点的下一个孩子结点的指针


表头数组的表头结点:


data(数据域) firstchild(头指针域)

存储某个结点的数据信息 存储该结点的孩子链表的头指针

bcff713717a24534b4c0b5b674f8acd8.png


优点:便于实现查找树中指定结点的孩子结点。


缺点:不便于查找指定结点的双亲结点。


⚡双亲孩子链表存储结构


与孩子链表存储结构类似,以一组地址连续的存储单元来存放树中的各个结点,每一个结点有三个域


数据域:存放该结点的值


父指针域:用于存放双亲结点在数组中的位置


子指针域:用于存放该结点的孩子链表的头指针。


e3a1af0b7435472d95278ee052d640d4.png


⚡孩子兄弟链表存储结构


孩子兄弟链表存放,又称为“左子/右兄”二叉链式存储结构。


左指针:指向该结点的第一个孩子


右指针:指向该结点的右邻兄弟


data(数据域) firstchild(指针域) rightsib(指针域)

存储结点的数据信息 存储该结点的第一个孩子的存储地址 存储该结点的右兄弟结点的存储地址

9b57fb1db8824839b545e1b9ba7744bd.png

相关文章
|
1月前
|
算法
数据结构之博弈树搜索(深度优先搜索)
本文介绍了使用深度优先搜索(DFS)算法在二叉树中执行遍历及构建链表的过程。首先定义了二叉树节点`TreeNode`和链表节点`ListNode`的结构体。通过递归函数`dfs`实现了二叉树的深度优先遍历,按预序(根、左、右)输出节点值。接着,通过`buildLinkedList`函数根据DFS遍历的顺序构建了一个单链表,展示了如何将树结构转换为线性结构。最后,讨论了此算法的优点,如实现简单和内存效率高,同时也指出了潜在的内存管理问题,并分析了算法的时间复杂度。
53 0
|
27天前
|
存储 缓存 算法
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式,强调了合理选择数据结构的重要性,并通过案例分析展示了其在实际项目中的应用,旨在帮助读者提升编程能力。
53 5
|
1月前
|
存储 搜索推荐 算法
【数据结构】树型结构详解 + 堆的实现(c语言)(附源码)
本文介绍了树和二叉树的基本概念及结构,重点讲解了堆这一重要的数据结构。堆是一种特殊的完全二叉树,常用于实现优先队列和高效的排序算法(如堆排序)。文章详细描述了堆的性质、存储方式及其实现方法,包括插入、删除和取堆顶数据等操作的具体实现。通过这些内容,读者可以全面了解堆的原理和应用。
89 16
|
1月前
|
算法
数据结构之文件系统模拟(树数据结构)
本文介绍了文件系统模拟及其核心概念,包括树状数据结构、节点结构、文件系统类和相关操作。通过构建虚拟环境,模拟文件的创建、删除、移动、搜索等操作,展示了文件系统的基本功能和性能。代码示例演示了这些操作的具体实现,包括文件和目录的创建、移动和删除。文章还讨论了该算法的优势和局限性,如灵活性高但节点移除效率低等问题。
54 0
|
2月前
|
存储 安全 数据库
除了 HashMap,还有哪些数据结构可以实现键值对存储?
【10月更文挑战第11天】 除了`HashMap`,其他常见支持键值对存储的数据结构包括:`TreeMap`(基于红黑树,键有序)、`LinkedHashMap`(保留插入顺序)、`HashTable`(线程安全)、`B-Tree`和`B+Tree`(高效存储大量数据)、`SkipList`(通过跳跃指针提高查找效率)及`UnorderedMap`(类似`HashMap`)。选择合适的数据结构需根据排序、并发、存储和查找性能等需求。
|
2月前
|
Java C++
【数据结构】探索红黑树的奥秘:自平衡原理图解及与二叉查找树的比较
本文深入解析红黑树的自平衡原理,介绍其五大原则,并通过图解和代码示例展示其内部机制。同时,对比红黑树与二叉查找树的性能差异,帮助读者更好地理解这两种数据结构的特点和应用场景。
42 0
|
2月前
探索顺序结构:栈的实现方式
探索顺序结构:栈的实现方式
|
1月前
|
C语言
【数据结构】栈和队列(c语言实现)(附源码)
本文介绍了栈和队列两种数据结构。栈是一种只能在一端进行插入和删除操作的线性表,遵循“先进后出”原则;队列则在一端插入、另一端删除,遵循“先进先出”原则。文章详细讲解了栈和队列的结构定义、方法声明及实现,并提供了完整的代码示例。栈和队列在实际应用中非常广泛,如二叉树的层序遍历和快速排序的非递归实现等。
210 9
|
1月前
|
存储 算法
非递归实现后序遍历时,如何避免栈溢出?
后序遍历的递归实现和非递归实现各有优缺点,在实际应用中需要根据具体的问题需求、二叉树的特点以及性能和空间的限制等因素来选择合适的实现方式。
37 1
|
1月前
|
存储 算法 Java
数据结构的栈
栈作为一种简单而高效的数据结构,在计算机科学和软件开发中有着广泛的应用。通过合理地使用栈,可以有效地解决许多与数据存储和操作相关的问题。

热门文章

最新文章