合并k个排序大小为n的数组的下界

时间:2017-10-10 10:41:31

标签: algorithm sorting merge time-complexity lower-bound

正如标题所暗示的那样,我想知道合并k个排序大小为n的数组下限的证明是什么?我知道界限是O(kn * log [k]),但这是如何实现的?我尝试比较使用决策树对p元素数组进行排序,但我不知道如何实现此证明。

3 个答案:

答案 0 :(得分:1)

这很容易证明,尝试以合并排序的方式考虑它。

合并排序大小 K * N 的数组取 O(KN * log(K * N))

但我们不必达到大小 1 leafs ,因为我们知道当数组大小为 N 时它会被排序。为简单起见,我们假设 K 是2的幂。

我们需要多少次除以2才能达到大小为N的叶子?
K 次!

<强>可视化 enter image description here


因此,您有 log(k)步骤,然后必须合并每个步骤 K N ,并且有 log(k)步骤。因此,时间复杂度 O(NK (log(K))


证明:
让我们假设它不是下限,我们可以做得更好。然后,对于任何大小 N * K 的未知数组,我们可以将其拆分为2,直到我们到达大小为 N 的子数组,对每个大小为N的数组进行合并排序在 Nlog(N)时间内以及所有阵列的总数 K * N * log(N)时间。

在对大小为N的K阵列进行排序后,我们必须将它们合并为更大的 N * K 阵列,支付小于 O(NK *(log(K) ),因为我们假设它不是下限。

最后,您排序了一个大小为N * K的未知数组,其复杂度小于 N * K * log(N * K),这在比较模型中是不可能的。
因此,在合并大小为N的K排序数组时,你不能比 O(NK *(log(K))更好。

答案 1 :(得分:1)

可能的实施。
让我们创建一个heap data structure来存储按元素排序的(element, arrayIndex)对。然后

  1. 将具有相应数组索引的每个数组的第一个元素添加到此堆中。
  2. 在每个步骤中,从堆中删除顶部(最低)对p,将p.element添加到结果中,然后将具有下一个元素的对(next, p.arrayIndex)插入堆中具有p.arrayIndex索引的数组(如果它不为空)。
  3. 对于跟踪'next'元素,您需要一个带有k索引/指针/迭代器的数组,这些数组指向相应数组的下一个元素。

    堆中最多会有k个元素,因此堆的insert / remove操作将具有O(log(k))复杂度。每个元素都将从堆中插入和删除一次。元素数量为n*k。总体复杂度为O(n*k*log(k))

答案 2 :(得分:0)

创建一个大小为k的最小堆,它存储来自每个k数组的下一个项目。每个节点还存储它来自哪个阵列。通过将堆中的min添加到final_sorted_array,然后将值中的下一个元素添加到堆中来创建排序数组。

删除堆的最小值是O(log k)。你有NK元素,所以你做NK次。最终结果:O(NK log k)。