试图理解“LibrarySort”?

时间:2014-01-02 05:26:13

标签: algorithm

我正在阅读"Insertion Sort is O(nlogn) by Michael A. Bender , Martín Farach-Colton , Miguel Mosteiro",我不太明白该算法的工作原理以及如何在Wikipedia的帮助下实现该算法。以下是从原始文章中提取的算法的描述。

  

1)设A是要排序的n元素数组。这些元素插入一个   随机顺序的时间到大小为(1 +ε)n的排序数组S.

所以第一步是创建大小(1 +ε)n的数组。设ε= 1,然后我需要创建一个大小比原始数组大两倍的数组。

  

2)插入按log(n)轮进行,如下所述。   每一轮将插入S中的元素数量加倍,并将元素所在的S前缀加倍。

据我所知,外循环将循环log(n)时间。每一轮,我需要将A(原始数组)中的元素数量加倍到S数组。 我真正理解的是“S的前缀加倍

  

3)具体地,当插入元素2 i 并且元素被重新平衡时,round i th 结束。在重新平衡之前,2 i 元素位于第一个(1 +ε)2 i 位置。   重新平衡将它们移动到第一个(2 +2ε)2 i 位置,传播   元素尽可能均匀。我们称2 +2ε扩展因子

据我所知,每一轮,我们都会做“重新平衡”。 “rebalance”会将原始元素均匀地分布在S数组中,以便在元素之间留下一些空隙。传播元素的公式是: k = i *(1 +ε)其中 i 是旧索引, k < / em>是一个新索引。

  

4)在第i轮 th 内插入2 i-1 插入元素   蛮力方式:搜索要插入的元素的目标位置   二元搜索(在S中的2个 i-1 支持位置中)和移动元素   更高等级为新元素腾出空间。并非所有元素都更高   需要移动等级,只有相邻数组位置的等级直到最近   差距被发现。

这部分展示了如何将每个元素插入到S数组中。首先,使用二进制搜索来搜索元素应该属于的位置。然后,转移更高的等级直到它达到差距。

这是我理解的算法的翻译(其中A是数组到排序,数组以索引1开始):

def LibrarySort(A)
    n ← length(A)
    S ← array of size (1 + ε) * n

    for i ← 1 to n
        S[i] = null

    for i ← 1 to floor(log(n) + 1)
        for j ← 2i - 1 to 2i
            index = binarysearch(S, A[j])
            insert(S, A[j], index)
        rebalance()

然后对于insertion()函数需要3个参数:array,要插入的项和location。

def insert(S, item, index)
    if S[index] != null
        tmp ← S[index]
        i ← index + 1
        while i <= length(S) and S[i] != null
           swap(tmp, S[i])
           i++
    S[index] ← item

问题

  • 我的理解是正确的吗?
  • 什么是“S的前缀加倍

1 个答案:

答案 0 :(得分:1)

Ad“将S的前缀加倍”:数组(内存)在开头分配一次,大小为(1 + ε n ,其中< em> n 是要排序的元素总数。但是元素是逐渐添加的,并且随着它们的添加,它们不会遍布整个数组,而只是它的一些前缀。当 m 元素重新平衡时,它们分布在数组的第一个(1 + ε m 元素中。这是前缀。当 m 加倍时,(1 + ε m 也是如此。

广告正确性:我看到一个小错误:

  

传播元素的公式是:k = i *(1 +ε)其中i是旧索引,k是新索引。

引用的描述没有说明公式是什么,但它不能是这个。因为这会将长度为 m 的数组映射到长度(1 + ε m ,但描述说您要映射长度数组(1 + ε m 到长度为2的数组(1 + ε m

一个简单的表达式是 k = 2 i 其中 i 索引,但那不会均匀地分散元素。要均匀地分布元素,公式为 k =(2 + 2 ε i ,但 i 是index 排除任何差距