【问题标题】:How do I change iterative quicksort with fixed pivot to iterative quicksort with random pivot?如何将具有固定枢轴的迭代快速排序更改为具有随机枢轴的迭代快速排序?
【发布时间】:2013-03-20 05:50:24
【问题描述】:

我发现此代码用于使用固定枢轴进行快速排序。它总是将给定表格的右侧元素作为枢轴。我希望它以随机元素为轴心。我认为x 在这里是一个支点,所以我认为将其更改为给定列表中的随机元素是个好主意,但事实证明它不起作用。

void swap ( int* a, int* b )
{
    int t = *a;
    *a = *b;
    *b = t;
}


int partition (int arr[], int l, int h)
{
    int x = arr[h];
    int i = (l - 1);
    for (int j = l; j <= h- 1; j++)
    {
        if (arr[j] <= x)
        {
            i++;
            swap (&arr[i], &arr[j]);
        }
    }
    swap (&arr[i + 1], &arr[h]);
    return (i + 1);
}

void quickSortIterative (int arr[], int l, int h)
{
    int stack[ h - l + 1 ]; 
    int top = -1;

    stack[ ++top ] = l;
    stack[ ++top ] = h;

    while ( top >= 0 )
    {
        h = stack[ top-- ];
        l = stack[ top-- ];

        int p = partition( arr, l, h );

        if ( p-1 > l )
        {
            stack[ ++top ] = l;
            stack[ ++top ] = p - 1;
        } 
        if ( p+1 < h )
        {
            stack[ ++top ] = p + 1;
            stack[ ++top ] = h;
        }
    }
}

我尝试换行

int x = arr[h];

swap(&arr[i+1], &arr[j]);

int r = l+rand()%(h-l);
int x = arr[r];

然后

swap(&arr[i+1], &arr[r]);

但它没有正确排序。显然我在这里做错了什么。请帮忙。

【问题讨论】:

  • 有什么理由用可变长度数组代替递归?它不会使您免于堆栈溢出。
  • @Alexey Frunze 这是我的大学运动。我应该比较不同种类的快速排序。递归没有问题(固定和随机枢轴),但迭代对我来说是一个问题。我最终使用了别人的代码,导致无法理解。

标签: c sorting quicksort


【解决方案1】:

您的分区函数假定枢轴位于分区的末尾。 考虑先将随机枢轴移动到分区的末尾。

即添加

swap(&arr[r], &arr[h]);

选择您的支点后。

【讨论】:

    【解决方案2】:

    问题在于“分区”函数现在移动了枢轴,因此它不会保留在r 索引处。并且该函数还遗漏了最后一个元素(在索引h 处)。 最简单的解决方案是在选择枢轴后将其放置在最右边的位置,并保持其他所有内容相同:将swap(&amp;arr[r], &amp;arr[h]); 放在partition() 的第一个循环之前,并将最后一个交换恢复为swap (&amp;arr[i + 1], &amp;arr[h]);

    【讨论】:

      猜你喜欢
      • 2018-11-14
      • 2011-08-31
      • 1970-01-01
      • 1970-01-01
      • 2010-09-14
      • 1970-01-01
      • 1970-01-01
      • 2012-12-20
      • 1970-01-01
      相关资源
      最近更新 更多