Heap Sort
前言
通过两天的时间终于看完了Heap Sort相关的内容,通过对于heap这一新的数据结构的学习,也算是初步理解了为什么算法和数据结构是密不可分的了,同时也对后面其他的数据结构及其对应算法产生了更浓厚的兴趣;当然在学习heap的过程中也遇到了一些令人头大的问题,尤其是关于计数问题,本文将梳理heap sort涉及到的二叉树的一些概念和一些学习思路。
HEAP
Heap是一种基于数组的新的数据的组织形式,传统的数组按照下表顺序连续的储存在内存中,同一数组中的元素间的联系在于内存地址连续。Heap虽然依赖于数组结构,但却采用了新的组织形式;Heap本质上是一种binary tree,而且这个树状结构仅可能最后一层不满,树中的元素和数组中的元素的下表的对应关系如下图:
根据需要,数组中的元素并不需要每一个都是heap中的元素,但heap中的元素在数组中下表一定是连续的。比如可以将A[1…10]视作heap(如上图),我也可以将数组中的部分元素A[2…9]视作heap,但绝不能将A[1…5,7…10]视作heap。
child & parent &root
子节点(child)、父节点(parent)和根节点(root)是分析树结构时重要的概念,我个人认为这三个概念是heap结构(由于目前本人只学过heap,并不了解树结构的其他性质)的核心。
叶子节点:没有子节点的节点,如上图中的6、7、8、9、10号节点
父节点(PARENT):与节点i直接连接的上一层的节点
PARENT(i) = ⌊i/2⌋
左子节点(LEFT):与节点i直接连接的左侧的子节点
LEFT(i) = 2i
右子节点(RIGHT):与节点i直接连接的右侧的子节点
PARENT(i) = 2i+1
在普通数组中我们绝不会认为第 i 号元素会和 2i 号元素存在什么直接联系,但heap结构建立了联系。
max-heap & min-heap
针对于heap这种结构,提出了两种特殊的heap,分别为max-heap和min-heap。
max-heap:A[PARENT(i)] ≥ A[i]
min-heap:A[PARENT(i)] < A[i]
在max-heap中,所有的父元素均大于或等于其对应的子元素,因此其root元素一定是所有元素中最大的。
在min-heap中,所有的父元素均小于其对应的子元素,因此其root元素一定是所有元素中最小的。
heap的部分性质
为方便后续讨论,先推出一些简单的性质作为引理。
首先声明:令k表示树的层,root节点位于k = 0层,S表示树中总的元素个数,Sk表示第k层中元素的个数,n表示树中元素的总个数。
借助上述符号表示如下性质:
树中共有:⌈ log 2 ( n ) \log_2^ (n) log2 (n)⌉层
S k = 2 k S_k = 2^k Sk=2k
满树时 : n = ∑ i = 1 k S i = 2 k + 1 − 1 n=\displaystyle\sum_{i=1}^{k} S_i=2^{k+1}-1 n=i=1∑kSi=2k+1−1
由上可知,第k层的第一个元素的序号为 2 k 2^k 2k。
引理:叶子元素的下表一定为⌊ n 2 \frac{n}{2} 2n⌋+1,⌊ n 2 \frac{n}{2} 2n⌋+2,…,n
证明:不妨假设最后一层(记为第 k k k层)一共有 x x x个元素
显然前 k − 1 k-1 k−1层一共有 ∑ i = 1 k − 1 S i = 2 k − 1 \displaystyle\sum_{i=1}^{k-1} S_i=2^{k}-1 i=1∑k−1Si=2k−1个元素,因此树中一共有[ 2 k − 1 + x 2^k-1+x 2k−1+x]个元素。
下面针对于x的奇偶性分开进行讨论
x = 2 y x=2y x=2y时(偶数)
树中一共有[