CLRS的D元堆问题


10

解决以下问题时我感到困惑(问题1-3)。

d进制堆就像是一个二进制堆,但(带有一个可能的例外)非叶节点具有d孩子而2个孩子。

  1. 您将如何在数组中表示d -ary堆?

  2. n个元素的d元堆的高度分别是nd

  3. d -max-heap中给出EXTRACT-MAX的有效实现。根据dn分析其运行时间。

  4. d-最大堆中给出INSERT的有效实现。根据dn分析其运行时间。

  5. 给出INCREASE-KEY(Aik)的有效实现,如果k <A [i] = k,则标记一个错误,然后适当地更新d -ary矩阵堆结构。根据dn分析其运行时间。

我的解决方案

  1. 给一个数组一个[一个1个一个ñ]

    一个1个1级一个2一个2+d-1个2级一个2+d一个2+d+d2-1个等级k一个2+一世=1个ķ-1个d一世一个2+一世=1个ķd一世-1个

    我的表示法似乎有点复杂。还有其他更简单的方法吗?

  2. h表示d -ary堆的高度。

    假设堆是完整的d元

    1个+d+d2++dH=ñdH+1个-1个d-1个=ñH=ØGd[ñd-1个+1个]-1个
  3. 这是我的实现:

    EXTRACT-MAX(A)
    1  if A.heapsize < 1
    2      error "heap underflow"
    3  max = A[1]
    4  A[1] = A[A.heapsize]
    5  A.heap-size = A.heap-size - 1
    6  MAX-HEAPIFY(A, 1)
    7  return max
    
    MAX-HEAPIFY(A, i)
    1  assign depthk-children to AUX[1..d]
    2  for k=1 to d
    3      compare A[i] with AUX[k]
    4      if A[i] <= AUX[k]
    5          exchange A[i] with AUX[k]
    6          k = largest
    7  assign AUX[1..d] back to A[depthk-children]
    8  if largest != i
    9      MAX-HEAPIFY(A, (2+(1+d+d^2+..+d^{k-1})+(largest-1) )
    
    • MAX-HEAPIFY的运行时间:

      其中 Ç 表示的成本上述第线。

      TM=d(c8d+(c9+..+c13)d+c14d)
      ci
    • EXTRACT-MAX:

      TE=(c1+..+c7)+TMCdh=Cd(logd[n(d1)+1]1)=O(dlogd[n(d1)])

    这是有效的解决方案吗?还是我的解决方案有问题?


我认为问题和解释中都存在一个小错误:dary堆的高度为h =(log [nd-n + 1])− 1 //注意其“ -n”而不是h = (log [nd−1+1])− 1因此不是“ -1”,因此我们上面对高度的解释将不成立。h = log [nd-1 + 1] -1 = log [nd] -1 = log [n]尽管如此,树的高度写为Θ(log(n)).注意:对于dary堆,log始终以基d为单位。
泗水拉吉2015年

Answers:


10
  1. 您的解决方案是有效的,并且遵循d -ary堆的定义。但是正如您指出的那样,您的表示法有些复杂。

    您可以使用这两个以下功能来检索父个元素和Ĵ的第子个元素。

    d-ary-parent(i)    return (i2)/d+1

    d-ary-child(i,j)    return d(i1)+j+1

    显然,。您可以验证那些函数来检查d-ary-parent d-ary-child i j = i1jdd-ary-parent(d-ary-child(i,j))=i

    同样容易看到的是,二进制堆是 -ary堆的特殊类型,其中d = 2,如果将d替换为2,则将看到它们与书中提到的函数PARENT,LEFT和RIGHT匹配。dd=2d2

  2. 如果我正确地理解了您的答案,您使用的是几何级数。在您的情况下,您可以得到,显然是 log dnh=logd(nd1+1)1,这实际上是一个有效且正确的解决方案。但是仅仅为了处理恒定的波动,您可能想要写 Θ log dn logd(nd)1=logd(n)+logd(d)1=logd(n)+11=logd(n)Θ(logd(n))

    cΘ

  3. AUXd-ary-parentd-ary-child

    EXTRACT-MAXMAX-HEAPIFYO(d logd(n(d1))

    O(d logd(n(d1)))=O(d(logd(n)+log(d1)))=O(d logd(n)+d logd(d1))

    dndlogd(d1)O(dlogd(n))MAX-HEAPIFYOΘ

  4. CLRS本书已经提供了INSERT程序。看起来像这样:

    INSERT(A,key)    A.heap_size=A.heap_size+1    A[A.heap_size]=    INCREASE-KEY(A,A.heap_size,key)

    O(logd(n))

  5. 就像INSERT一样,INCREASE-KEY在课本中也定义为:

    INCREASE-KEY(A,i,key)    if key<A[i]        error"new key is smaller then current"    A[i]=key    while i>1 and A[i]>A[d-ary-parent(i)]        A[i]A[d-ary-parent(i)]        i=d-ary-parent(i)

    O(logd(n))


谢谢!如何实现INCREASE-KEY和INSERT?我尝试编写它,但是它给了两次MAX-HEAPIFY递归调用。有更好的解决方案吗?我发现网络和信息的小维基
lucasKo

剩下的运动吗?如果是这样,请更新您的问题,我们将很乐意回答主题。
Bartosz Przybylski 2012年

我把那些问题放在编辑过的帖子上。
lucasKo 2012年

重现INSERT程序?您的意思是,在插入新元素之后,不必调用调整堆中顺序的过程吗?我不明白...
lucasKo 2012年

该描述有点不幸,请参阅编辑以进行澄清。
Bartosz Przybylski 2012年

1

h=logd[nd1+1]1
1+d+d2+..+dh=ndh+11d1=nh=logd[n(d1)+1]1
h=Θ(logd(n))

-1

第二个问题的答案是h = log d(n(d-1)+1)-1所以,h = log d(nd-n + 1)-1


4
为什么这是答案?没有解释的公式并不能真正帮助任何人。
David Richerby '16
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.