免费版:数据结构二叉树之闲死攻略
接上一篇《数据结构二叉树之闲死攻略(一)》
不要难过,其实数据结构是很有趣的,很......
目录
4 二叉搜索树(Binary Search Tree)
4.1 BST的特性
(1) 顺序性(左<根<右)
(2)单调性(小到大)
BST的中序遍历序列,必然单调非降。最左的为最小的,最右的为最大的。
4.2 BST的查找
查找22,22>16,跳到16的右子树,22<25,跳到25的左子树,22>19,跳到19的右子树,找到了22。
查找的效率决定于树的高度,若树的高度是h,那么查找过程的时间复杂度就是O(h)。
4.2 BST的插入
关键是要找到元素应该插入的位置,可以采用与Find类似的方法
4.3 BST的删除
考虑三种情况
(1)要删除的是叶结点
直接删除,并再修改其父结点指针---置为NULL
(2)要删除的结点只有一个孩子结点
将其父结点的指针指向要删除结点的孩子结点
(3)要删除的结点有左、右两棵子树
用另一结点替代被删除结点:右子树的最小元素 或者 左子树的最大元素
插入一道小库科技的笔试题:
给予一个二叉树的根节点,验证该树是否是二叉搜索树,在O(n)时间内,用熟悉的语言写出算法。
5 线索二叉树
传统的链式存储仅能表现一种父子关系,不能直接得到结点在遍历中的前驱或后继。
为了加快查找前驱和后继的速度,引入了线索二叉树。
线索二叉树的结点结构
以中序线索二叉树的建立为例(BDAEC)
pre指向中序遍历时上一个刚刚访问过的结点。
二叉树是一种逻辑结构,线索二叉树是加上线索(指针)后的链表结构,是二叉树在计算机内部的一种存储结构,所以是一种物理结构。
6 优先队列与堆
发送到打印机的作业一般会被放到队列中,但这未必是最好的做法。例如,有一项作业特别重要,希望只要打印机一空闲就来处理这项作业,这时就需要为该作业赋予优先权。这种应用的实现需要一类特殊的队列,称之为优先队列。
优先队列(Priority Queue):特殊的“队列”,取出元素的顺序是依照元素的优先权(关键字)大小,而不是元素进入队列的先后顺序。
5.1 如何实现优先队列?
5.1.1 采用数组或链表实现优先队列
5.1.2 采用二叉堆实现优先队列
二叉堆简称为堆。
堆有两个特性:
(1)结构性
堆本质上是一棵用数组表示的完全二叉树。
对于一棵有n
个结点的完全二叉树,对其结点按层序编号,从上到下,从左到右,对任一结点i (1 = i <= n)
有:
- 如果
i = 1
,则结点i
是二叉树的根,无父结点;如果i > 1
,则其父结点的位置是⌊i / 2⌋
(向下取整)。 - 如果
2i > n
,则结点i
无左孩子(结点i
为叶子结点);否则其左孩子是结点2i
。 - 如果
2i + 1 > n
,则结点i
无右孩子;否则其右孩子是结点2i + 1
。
得益于二叉树的严格定义,我们只需要把完全二叉树按层序遍历依次把结点存入一维数组中,其数组下标就能够体现出父子结点关系(数组第0位不使用)。
(2)有序性
任一结点的关键字是其子树所有结点的最大值(或最小值)
最大堆(MaxHeap),也称“大顶堆”:最大值
最小堆(MinHeap),也称“小顶堆” :最小值
栗子:对最小堆用筛选法SiftDown调整
根结点72在其左右子子结点里找到最小的结点,与之交换。72 - 05
72 - 16
最大堆的建立
建最小堆
从23开始,05与71换
接着调73,shiftdown
此时72的左右子树都已经是子堆了
最小堆删除元素
栗子1:删除68
首先拿位于最后的元素45去替换
对45进行shiftup
栗子2:删除16
还是拿位于最后的元素45去替换
对45进行shiftdown
建堆效率分析
最小堆操作效率
优先队列的操作(等价于对堆进行插入与删除操作):
(1)入队
(2)出队