版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、2020/11/12,堆与优先队列,1,第九章 堆与优先队列 理解以集合为基础的抽象数据类型优先队列。 理解用有序字典实现优先队列的方法。 理解优先级树和堆的概念。 掌握用数组实现堆的方法。 理解以集合为基础的抽象数据类型可并优先队列。 理解左偏树的定义和概念。 掌握用左偏树实现可并优先队列的方法。 掌握堆排序算法。,2020/11/12,堆与优先队列,2,9 堆与优先队列,9.0 优先队列的原型 排队上车,老弱病残者优先上车 排队候诊,危急病人优先就诊 洗相馆为顾客洗照片,加钱加急者优先洗 分时操作系统运行程序,小程序优先 贪心算法对解分量的选择,按元素的某种特征值,大(或小)的优先 在一个
2、集合中搜索,按元素的某种特征值,大(或小)的优先 处理或服务时只关心对象中谁的优先级最高通常的队列是一种优先队列最先到者优先级最高,2020/11/12,堆与优先队列,3,9 堆与优先队列,9.1 优先队列的定义 优先队列也是一个以集合为基础的抽象数据类型。 优先队列中的每一个元素都有一个优先级值。优先队列中元素x的优先级值记为p(x),它可以是一个实数,也可以是一个一般的全序集中的元素。优先级值用来表示该元素出列的优先级。 通常约定优先级值小的优先级高。也可以约定优先级值大的优先级高。 优先队列支持的基本运算有: (1)Size( ):返回优先队列中元素个数。 (2)Min( ):返回优先队
3、列中具有最小优先级值的元素。 (3)Insert(x):将元素x插入优先队列。 (4)DeleteMin(x):删除优先队列中具有最小优先级值的元素,并保存到x中。,2020/11/12,堆与优先队列,4,9 堆与优先队列,9.2 用实现有序字典的方式实现优先队列 (1)优先队列与字典的相似性与区别: 优先队列中元素的优先级值可以看作是有序字典中元素的线性序值。 在有序字典中,不同的元素具有不同的线性序值,其插入运算仅当要插入元素x的线性序值与当前字典中所有元素的线性序值都不同时才执行。 对于优先队列来说,不同的元素可以有相同的优先级值。因此,优先队列的插入运算即使在当前优先队列中存在与要插入
4、元素x有相同的优先级值的元素时,也要执行元素x的插入。,2020/11/12,堆与优先队列,5,9 堆与优先队列,9.2 用实现有序字典的方式实现优先队列 (2)由于优先队列与字典的相似性,除了散列表之外,所 有实现字典和有序字典的方法都可用于实现优先队列。 用有序链表实现优先队列;(Insert低效) 用二叉搜索树实现优先队列;(Insert,DeleteMin, Min 均低效) 用AVL树实现优先队列;(逻辑复杂) 用无序链表实现优先队列;(DeleteMin, Min均低效) 都有缺点。原因在于没有考虑到优先队列的特性。,2020/11/12,堆与优先队列,6,9 堆与优先队列,9.3
5、 用优先级树实现优先队列 1.优先队列的特征: DeleteMin和Min只关心优先级最高的元素 Insert的元素不要求全局的序关系 因此实现优先队列的结构只要求方便DeleteMin和Min,而对Insert也只要求不给结构的维护带来太大的麻烦。 根据这两个特征,人们发明了优先级树。,2020/11/12,堆与优先队列,7,9 堆与优先队列,9.3 用优先级树实现优先队列(续) 2.优先级树的概念 优先级树是满足下面的优先级性质的二叉树: (1)树中每一结点存储一个元素。 (2)任一结点中存储的元素的优先级值不大(小)于其儿子结点中存储的元素的优先级值即父结点的优先级不低于其儿子结点的优先
6、级。 换句话说,越接近根的结点中的元素的优先级越高,越方便被访问,因为根最方便被访问。 相应的优先级树称为极小(大)化优先级树。,2020/11/12,堆与优先队列,8,9 堆与优先队列,9.4用堆实现优先队列 用优先级树实现优先队列仍有不足: Insert(x)和DeleteMin(x)后对结构的维护,在最坏情况下,仍需O(h)=O(n)。 如果让优先级树近似满,从而h=log n,达到最小,那么,结果将令人满意:在最坏情况下, Min( )将只需O(1), Insert(x)和DeleteMin(x)后对结构的维护只需O(log n)。 因而引入堆的概念并用堆来实现优先队列。 (1)堆的概
7、念: 如果一棵优先级树是一棵近似满二叉树,那么,这棵具有优先级性质的近似满二叉树(外形像堆)就叫做堆。 (2)用堆实现优先队列: Min( )、Insert(x)和DeleteMin(x)运算的实现,2020/11/12,堆与优先队列,9,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (1) 用数组表示堆: 从1开始对堆的结点从根开始自上而下逐层、每层从左到右进行编号,然后让结点中的元素按编号在数组A中与下标对号入座。 (2) 用数组表示堆的优点: 存储紧凑,空间利用率高 父子关系简单清晰:存放在Ai的是结点i的元素, A2i和A2i+1分别是结点i的左和右儿子结点2i和2i+1的元
8、素, Ai/2是结点i的父结点的元素,2020/11/12,堆与优先队列,10,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列(续) (3)数组实现优先队列极小化堆类MinHeap的定义 template class MinHeap private: int Last, MaxSize;/ Last和MaxSize分别是堆和 /数组的最大下标 T *heap; / 元素数组 public: MinHeap(int MinHeapSize = 10); MinHeap() delete heap; int Size( ) const return Last; ,2020/11/12,堆与
9、优先队列,11,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (3)数组实现优先队列极小化堆类MinHeap的定义(续) T Min( ) if (Last = 0) throw OutOfBounds(); return heap1; MinHeap ,2020/11/12,堆与优先队列,12,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 构造函数(初始化一个空堆) template MinHeap:MinHeap(int MinHeapSize) MaxSize = MinHeapSize; heap = new TM
10、axSize+1; Last = 0; ,2020/11/12,堆与优先队列,13,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 插入函数Insert(x) template MinHeap ,2020/11/12,堆与优先队列,14,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 优先级值最小者出列函数DeleteMin(x) template MinHeap / ci 是i的左儿子结点,2020/11/12,堆与优先队列,15,9 堆与优先队列,9.5 用数组表示堆从而
11、实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 优先级值最小者出列函数DeleteMin(x)(续) while (ci heapci+1) ci+; if (y = heapci) break; /找到合适的已腾出的位置i heapi = heapci; / 小儿子上升,腾出位置 i = ci; /腾出的位置下降 ci *= 2; / ci是i的左儿子结点。继续测试 heapi = y; /在腾出的位置i插入y return *this;,2020/11/12,堆与优先队列,16,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中
12、未实现的函数 以已知数组的元素为元素初始化Initialize一个堆 template void MinHeap:Initialize(T a , int size, int ArraySize)/ArraySize和size分别是数组和其中有效数据的最大下标 delete heap; heap = a; Last = size; MaxSize = ArraySize;,2020/11/12,堆与优先队列,17,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 以已知数组的元素为元素初始化Initialize一个堆(续) for (i
13、nt i = Last/2; i = 1; i-) T y = heapi;/i的左右子树已堆化,今堆化以为i根的子树 int c = 2*i; / c是结点i的左儿子结点 while (c heapc+1) c+; if (y = heapc) break; heapc/2 = heapc; c *= 2; heapc/2 = y; ,2020/11/12,堆与优先队列,18,9 堆与优先队列,9.5 用数组表示堆从而实现优先队列 (4) 极小化堆类MinHeap定义中未实现的函数 (续)初始化Initialize一个堆的复杂性 上述算法的while循环耗时O(hi),其中hi是以结点i为根
14、的子树的高度。由于近似满二叉树a1:n的高度为h=logn,第j层结点个数至多为2j,因此至多有2j棵高度为hi=h-j的子树。从而算法的所有while循环共耗时 由此即知,算法Initialize所需的计算时间是O(n)。,2020/11/12,堆与优先队列,19,9 堆与优先队列,9. 5 用数组表示堆从而实现优先队列 (5)堆的应用堆排序及其复杂性 template void HeapSort(T a , int n)/n是数组的有效数据的最大下标 MinHeap H(1);/O(1) H.Initialize(a,n,n); / 建初始堆,O(n) T x; for (int i =
15、1; i = n; i+) / 相继n次从堆中抽取最小元 H.DeleteMin(x);/O(logn) ai = x;/O(1) /a1.n已按从小到大排好序,O(nlogn) H.Deactivate( );/O(1),为何不对H使用析构函数? /O(nlogn),2020/11/12,堆与优先队列,20,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.1 问题的提出 已知一个文本文件,要求把它转换成一个电子文档,以便存储在磁介质中或在网络上传输。从存储的角度看,我们自然希望该电子文档越短越好即存储占用的空间越少越好;从传输的角度看,我们自然也希望该电子文档越短越好即传
16、输占用的时间越少越好。因此,我们要求转换成的电子文档尽量地短,尽量地压缩。 有许多名家说过,把一个问题表述清楚了,就已经解决了问题的一半。这说明问题的表述很重要,表述得越清楚、越精确,对问题的解决越好。 上述问题还需要更精确的表述。,2020/11/12,堆与优先队列,21,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.2 表述Huffman编码问题的准备 对涉及的有关对象、概念、术语、和记号的准备 一个文本文件就是一个字符串,记为F。 文本文件中所用到的不同的字符组成的集合,记为C。 C中的字符c在文件中出现的频率/次数,记为f(c)或fc。 字符的编码0/1串。如字符
17、a的ASCII码是01100001。 字符编码的码长0/1串的串长。记cC的码长为l(c)。 文件F编码的码长原文本文件编码后的0/1串的累计长。记为L(F)=cC f(c)* l(c) 。 字符的定长编码。 ASCII码是一种定长编码。不可能压缩。 字符的变长编码字符的码长随字符而变。,2020/11/12,堆与优先队列,22,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.2 表述Huffman编码问题的的准备(续) 编码与解码既要编码又要解码,以便复原文件。 二义性:不能造成一串编码有两种理解。 前缀码:为了解码时不会出现二义性,要求任意一个字符的编码不能是另一个字符
18、的前缀。 字符集C的前缀码的表示以C中的字符为叶结点的二叉树,如a0,b101,c100,d111,e1101,f1100 可表示成右图的二叉树。 这棵树叫字符集C的前缀编码树,记为T。,2020/11/12,堆与优先队列,23,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.3 Huffman编码问题的表述问题数学化 经上述准备,我们看到,字符cC的码长l (c)正是c在字符集C的前缀编码树T中的深度,记为dT(c)。这样,我们的问题可更具体、更精确地表述为:已知字符串F和出现在F中的字符集C及C中每一字符c出现的频率/次数f(c) ,要求C的一棵最优的前缀编码树T, 使
19、得F的编码长cC f(c)* dT(c) B(T)达到最小。这棵最优的前缀编码树叫Huffman编码树。相应的前缀编码叫Huffman编码。,2020/11/12,堆与优先队列,24,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.4 求解问题的设想与分析 (1) 问题的目标是求C的最优前缀编码树T,因此,我们应该先分析一下C的最优的前缀编码树T的性质:它是一棵以C中的字符为叶结点的健全二叉树(这容易用反证法加以证明)。 因而一定有两个最深的叶结点是兄弟结点。 (2) 按照大数学家、大教育家波利亚的观点,“除数学和论证逻辑外,我们所有的知识都是由一些猜想所构成的。” 为了得
20、到有用的结论、方法,总是从猜想开始。而猜想的依据是合情推理。 就摆在面前的问题而言,可直观地设想:最深的叶结点中有两个兄弟是C中频 度最低的字符x和y ,因为编码最长的字符应该是频度最低的字符(这需要证明)。,2020/11/12,堆与优先队列,25,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.4 求解问题的设想与分析(续) (3) 用字符z代替字符x和y ,让f(x)+f(y)作为字符z 的频度f(z),相应地,在T中删去兄弟叶结点x和y ,而且用z 取代已经成为叶结点的x和y的父结点,得到一棵新的健全二叉编码树T,那么,T应该是C-x,yz的最优前缀编码树(这需要证
21、明) 。 若上述设想与分析正确,那么,问题就有了解法:把C中的字符以其频度为优先级值,且以小者优先组织成优先队列Q。然后反复地执行下面两个语句: 删除Q中优先级最高的两个字符,设为x和y; 虚拟字符z(分别以x和y为左和右儿子),并赋予优先级值f(z)=f(x)+f(y),插入Q; 直到Q为空,其结果就是C的最优前缀编码树。,2020/11/12,堆与优先队列,26,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.5 Huffman编码问题的解决 从理论上看待Huffman编码问题,在9.6.4 求解问题的设想与分析中的(2)和(3)所猜想的分别是问题的解的贪心选择性质和最
22、优子结构性质。这两个性质保证了问题可以用基于优先队列的前述算法正确地加以求解。所以问题的真正解决有待对贪心选择性质和最优子结构性质作理论上的证明。此外,还得给出Huffman编码和解码的简洁实现。,2020/11/12,堆与优先队列,27,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.5 Huffman编码问题的解决(续) (1) 问题解的贪心选择性质:设x和y是C中具有最小频度的两个字符,则存在C的一个最优前缀码使x和y具有最长的相同码长且仅最后一位编码不同,即x和y是编码树中最深的一对叶结点兄弟。,2020/11/12,堆与优先队列,28,9 堆与优先队列,9.6 优
23、先队列的应用Huffman编码 9.6.5 Huffman编码问题的解决(续) (2) 问题解的最优子结构性质:设x和y是C的最优编码树T中的两个叶子且为兄弟,z是它们的父亲。若将z看作是具有频率f(z)=f(x)+f(y)的字符,则树 T=T-x,y表示字符集C=C-x,yz的最优编码树。,2020/11/12,堆与优先队列,29,9 堆与优先队列,9.6 优先队列的应用Huffman编码 9.6.5 Huffman编码问题的解决 (3) Huffman编码和解码的简洁实现 从算法的动画演示中已经看到了Huffman编码和解码的一种实现方式。它们的简洁表述作为练习。,2020/11/12,堆
24、与优先队列,30,9.5 可并优先队列,9.5.1 问题的提出 用堆来实现优先队列,可在O(logn)的时间内支持同一优先队列中的基本运算(min,insert,和deletemin)。 现在如果要合并2个不同优先队列为一个优先队列,那么还用堆来表示优先队列,能不能在O(logn)的时间内既支持同一优先队列中的基本运算(min,insert,与 deletemin)又支持合并2个不同优先队列为一个优先队列的运算(concatenate)即可并优先队列? 不能 怎么办呢? 寻找另一种表示方式,2020/11/12,堆与优先队列,31,9.5.2 问题解决方案的设想与分析 首先想到的表示结构自然是
25、在优先级树的基础上加以改造, 因为它至少能很好地支持min运算。 剩下的只要很好地支持运算insert,deletemin 和concatenate。 这三种运算中最基本的运算是什么?合并concatenate 。因为另外两个运算都可以用它来实现: 运算insert(x)可以看成是要插入的可并优先队列与单个元素x的可并优先队列的合并。 运算deletemin( )可以看成是删掉min(根)后两棵优先级子树分别表示的两个可并优先队列的合并。而两个可并优先队列的合并可以转换成沿着从其中一个根到某叶(比如最右叶)的一条路上的子可并优先队列与另一个可并优先队列的合并。 因此,若沿路的合并在最坏情况下与
26、路长成正比,那么,只要此路长为O(logn),问题就解决了。 于是想出了左偏(高/重)的优先级树,简称左偏树。,2020/11/12,堆与优先队列,32,9.5 可并优先队列,9.5.2 左偏树的定义 左偏树是一类特殊的优先级树。与优先级树类似,也有极小化 左偏树与极大化左偏树之分。下面只讨论极小化左偏树。 在优先级树T中引入前端结点,得增广优先级树T。规定T的所 有前端结点的高度/重量为-1/0。对于T中任意非前端结点x, 分别递归定义其高度s(x)和重量w(x)为: s(x) = min s(L),s(R) + 1和w(x) = w(L) + w(R) + 1 其中L和R分别是结点x的左儿
27、子结点和右儿子结点。 一棵优先级树T是一棵左偏高/重树,当且仅当T的每个非终端 结点处,其左儿子结点的高度s/重量w 大于或等于其右儿子结 点的高度s/重量w。 左偏高树和左偏重树通称为左偏树。下面只讨论左偏高树。,2020/11/12,堆与优先队列,33,9.5 可并优先队列,9.5.3 左偏高树的性质 设x是一棵左偏高树T的任意一个结点(T的非前端结点) ,则 (1)T的以x为根的子树中至少有2 s(x)-1个结点。 (2)若T的以x为根的子树中有m个结点,则s(x)的值不超过log(m+1). (3)从x出发的最右路经的长度恰为s(x)。 证明:设结点x位于树T的第k层。由s(x)的定义
28、知,以x为根的子 树在T的第k+j层的每个结点恰有2个儿子结点,0 j s(x)-1。 因此,以x为根的子树在T的第k+j层恰有2j个结点。从而,以x为 根的子树中至少有 个结点,即(1) 成立。 由(1)可立即推出(2)。由s(x)的定义,以及在左偏高树中每个结点处,其左儿子结点的s值大于或等于其右儿子结点的s值,即可推出(3)。,2020/11/12,堆与优先队列,34,9.5 可并优先队列,9.5.4 用左偏高树实现可并优先队列 1.左偏树的结点类型HBLTNode说明 template class HBLTNode friend MinHBLT; public: HBLTNode(co
29、nst T ,2020/11/12,堆与优先队列,35,9.5.4 用左偏高树实现可并优先队列 2.用左偏树实现的可并优先队列MinHBLT的说明 template class MinHBLT public: MinHBLT( ) root = 0; MinHBLT( ) Free(root); T Min( ) if (!root) throw OutOfBounds( ); return root-data; MinHBLT,2020/11/12,堆与优先队列,36,9.5 可并优先队列,9.5.4 用左偏高树实现可并优先队列 3.可并优先队列MinHBLT的定义中未实现的函数 释放可并优
30、先队列t占用的空间:Free(t) template void MinHBLT:Free(HBLTNode *t) if (t) Free(t-LeftChild); Free(t-RightChild); delete t; ,2020/11/12,堆与优先队列,37,9.5 可并优先队列,9.5.4 用左偏高树实现可并优先队列 3.可并优先队列MinHBLT的定义中未实现的函数 (2)私有函数Concatenate(x, y)/可并优先队列的关键函数 template void MinHBLT:Concatenate(HBLTNode* / 现在 x-datadata,2020/11/12,堆与优先队列,38,9.5 可并优先队列,9.5.4 用左偏高树实现可并优先队列 3. 可并优先队列MinHBLT的定义中未实现的函数 (2) 私有函数Concatenate(x, y)(续) Concatenate(x-RightChild,y); /递归让y与x的右子树合并 if (!x-LeftChild) /合并后的 x的左子树为空树 / 交换合并后的 x的左、右子树 x-LeftChild = x-RightChild; x-RightChild = 0; x-s = 1; else / 若合并后的x的右子树较高则交换其左、右子树 if (x-LeftChild-s Ri
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 采购阶段成本控制制度
- 采购项目监督制度
- 采购风险点控制制度
- 钢厂采购部管理制度
- 2025年前台沟通能力模拟卷
- GB 46768-2025 有限空间作业安全新标准解读
- 第19章 二次根式基础卷(试题版A4)-人教版(2024)八下
- 第7章 相交线与平行线(章节复习检测培优卷)原卷版-人教版(2024)七下
- 2026年投资产业合同(1篇)
- 道法依宪治国教学课件-2025-2026学年统编版道德与法治八年级下册
- (高清版)DZT 0004-2015 重力调查技术规范(150 000)
- 营销负责人的优势和劣势
- 光纤传感监测技术
- 加油站防雷应急预案
- 换季衣物收纳整理课件
- 人教版八年级数学下册 (勾股定理)课件
- 配电线路及设备巡视
- 蕉岭县幅地质图说明书
- 小班数学认识数字1-5
- 湘教版(2019)高中地理必修二知识点汇编(全一册)
- 小学科学教育科学三年级上册水和空气 宋伟空气占据空间吗说课稿
评论
0/150
提交评论