1
merge1(int low, int high, int S[], U[]) 
{ 
    int k = (high - low + 1)/2
    for q (from low to high) U[q] = S[q]
    int j = low 
    int p = low 
    int i = low + k 

    while (j <= low + k - 1) and (i <= high) do 
    { 
        if ( U[j] <= U[i] ) 
        {
            S[p] := U[j] 
            j := j+1
        } 
        else 
        { 
            S[p] := U[i] 
            i := i+1 
        } 
        p := p+1 
    } 

    if (j <= low + k - 1) 
    { 
        for q from p to high do 
        { 
            S[q] := U[j] 
            j := j+1 
        } 
    }
}


merge_sort1(int low, int high, int S[], U[]) 
{ 
    if low < high 
    { 
        int k := (high - low + 1)/2 
        merge_sort1(low, low+k-1, S, U) 
        merge_sort1(low+k, high, S, U) 
        merge1(low, high, S, U) 
    } 
}

所以,基本上,这是在我的讲义上。总的来说,我觉得这很令人困惑,但我理解其中最大的部分。我不明白的是“if (j <= low + k - 1)”部分的需要。看起来它检查左侧是否有任何元素“左侧”。合并排序时甚至可能吗?

4

1 回答 1

2

合并两个排序列表(我们称它们为leftand right)时,您会不断地取出一个项目并将其添加到列表中,直到or列表result中的项目用完为止。这是由第一个循环完成的。现在您需要将左侧或右侧列表中剩余的元素添加到结果列表中。有两种选择:leftrightwhile

  • 左边的列表没有元素,右边的列表还有一些。这里代码的编写方式,我们不需要做任何事情,因为S数组的末尾已经包含了right列表中的最后一个元素。

  • 右边的列表没有元素,左边的列表还有一些。然后我们将剩余的元素复制到S. 这就是if结尾的merge1作用。


关于您的问题,如果此代码“错误”:代码是正确的,但我会进行一些更改以使其更具可读性:

  • 描述性变量名称。
  • 传递分隔leftright列表的中点,merge1而不是重新计算它。
于 2010-04-23T23:45:01.503 回答