《算法导论》第二十章febonacci heap_斐波纳契堆的实现

对于febonacci heap的分析:1.extract-min,抽取最小结点花销O(D(n))。因为将min[H]抽取出时,需要实际花销O(D(n))将其子结点并入根表中;其次,合并同度根结点时,由于根表此时最多有T(n)+D(n)-1个根结点,故将同度根结点链接时T
摘要由CSDN通过智能技术生成

对于febonacci heap的分析:

1.extract-min,抽取最小结点花销O(D(n))。因为将min[H]抽取出时,需要实际花销O(D(n))将其子结点并入根表中;其次,合并同度根结点时,由于根表此时最多有T(n)+D(n)-1个根结点,故将同度根结点链接时T(n)+D(n)-1至多实际花销O(T(n)+D(n)),合并后根表至多有D(n)+1个根。利用势能分析法,平摊代价为O(D(n))。其实,由实际代价O(T(n)+D(n))平堆代价为D(n),其实是由根链接减少导致势能减少来支付的。


2.decrease-key,设联级删除c个结点,则根结点由T(n)变为T(n)+(c-1)+1,(c-1个联级点,1个x删除点),势能由T(n)+m(H)变为T(n)+c+2*(m(H)-c+2),故O(c)+4-c=O(1)代价。为什么级联删除c个结点的代价,却是O(1)呢?而不是最坏情况O(lgn)?原因是当删除一个内结点的孩子时,若marked=FALSE,则置为TRUE,有2个“能”,一个用于删除自己,一个用于存储至根,以便同度的根合并。


3.delete-key,调用一次O(1)的decreate-key和O(D(n))的extract-min,故代价为O(D(n))。


4.势能函数T(n)+2*m(H),其中T(n)为根结点、m(H)为marked为TRUE的结点。Why? 斐波那契堆有一个非常重要的性质:度为d的根结点至少有Fd+2个结点,(注:Fi为febonacci数,0 1 1 2 3 5 8 13 ...)以保持D(n)在logn级,这样extract-min和delete-key只需O(logn)。

如何保持此性质呢?1.两个度数相同的根堆合并成二项堆;2.当删除第二个非根结点的孩子时,将该结点移至根形成一新堆。以下为数学证明:

当删除一个结点x时,令y=parent[x]。若marked[y]=TRUE,表明y已经删除1个结点,设D(x)为x结点的度数,x为y的第i个结点,则按照1同度合并操作,当初x与y合并时,x和y都有i-1个度。y至多被删除1个结点,故第y的i个子结点至少有i-2个度。可证size(x)等于size(i)+1,其中,假设size(i)>=Fd+2,归纳法即可证明size(x)>=Fd+2。

又n >= Fd+2 >= 1.56^d,(后Fd+2 >= logn可证),故d<=log1.56(n),即logn。证毕。

这说明只要保证extract-min和delete-key就可lazily维护“松散"的斐波纳契堆性质。而其它时候对于其结构,则允许“无限”松散。


5.对于D(n)如何选取呢?

1.Dn = 1+8*sizeof(long)——由于利用long类型定义堆的度的个数sizeof(long)*8,考虑到可能合并后最大度+1,故二项树度最多不超过1+sizeof(long)*8。
2.利用ceillog2函数,求出当前树结点n的最大度lgn,再+2。


以下是我对于febonacci heap的实现源代码:</

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值