具有重复键的快速排序算法
Posted
技术标签:
【中文标题】具有重复键的快速排序算法【英文标题】:Quicksort algorithm with duplicate keys 【发布时间】:2012-01-26 21:19:59 【问题描述】:我正在尝试实现快速排序算法。以下代码适用于唯一元素,但不适用于具有重复元素的数组。请告诉我我在哪里做错了。此外,当我将枢轴的值更改为 0 以外的其他数字时,程序崩溃。代码如下:
#include <iostream>
#include <cstdlib>
using namespace std;
void swapme(int &a, int &b)
int temp = a;
a = b;
b = temp;
void quicksort(int *arr, int size)
// these two variables will take care of position of comparison
int lower = 0, upper = size - 1;
int pivot = 0; // assigns pivot
if (size <= 1)
return;
while (lower < upper)
while (arr[lower] < arr[pivot])
++lower;
while (arr[upper] > arr[pivot])
--upper;
if (upper > lower)
swapme(arr[upper], arr[lower]);
// upper--;
// lower++;
quicksort(arr, lower);
quicksort(&arr[lower + 1], size - 1 - lower);
int main()
int arr[30];
for(int j = 0; j < 30; j++)
arr[j] = 1 + rand() % 5000;
for(int j = 0; j < 30; j++)
cout << arr[j] << "\t";
cout << endl;
quicksort(arr, 30);
for(int j = 0; j < 30; j++)
cout << arr[j] << "\t";
cout << endl;
cin.get();
cin.get();
更新:我终于成功了。这是固定版本:
void swapme(int &a, int &b )
int temp = a;
a = b;
b = temp;
void quicksort(int *arr, int size)
if (size <= 1)
return;
// These two variables will take care of position of comparison.
int lower = 0;
int upper = size-1;
int pivot = arr[upper/2]; // assigns pivot
while (lower <= upper)
while (arr[lower] < pivot)
++lower;
while (arr[upper] > pivot)
--upper;
if (upper >= lower)
swapme(arr[upper],arr[lower]);
if(arr[upper] == arr[lower])
// Can either increment or decrement in case of duplicate entry
upper--; // lower++;
quicksort(arr, lower);
quicksort( &arr[lower+1], size-1-lower);
【问题讨论】:
调试发现了什么? 我不知道枢轴位置问题。似乎发生了无限循环。 这不是作业,因为我不是 CS 学生 Bragboy:它是 C++,而不是 Java(对于有经验的程序员可能会有所帮助,但在我看来并非如此。) 【参考方案1】:您将枢轴元素的 索引 存储在 pivot
变量中,因此交换元素可能会在循环期间更改枢轴元素的选择。不是一个很好的主意。我建议将枢轴元素的实际 值 存储在 pivot
中。
另外,如果这真的不是功课,为什么不简单地使用标准库设施?
#include <algorithm>
// ...
std::sort(arr + 0, arr + 30);
您将获得经过高度优化和测试的代码,其性能将随时优于您的手写快速排序。
【讨论】:
关于面试问题的恐怖故事似乎足以激励我。【参考方案2】:可以实现任意数量的 i/p 整数的快速排序。它还处理重复键
#include <conio.h>
#include <string>
using namespace std;
void InputArray(int*,int);
void QuickSort(int *,int,int);
int partition(int *,int,int);
void swap(int *,int,int);
void printArr(int *,int Siz=11);
void main()
int siz;
cout<<"Enter Array length : "; cin>>siz;
int *a=new int[siz];
InputArray(a,siz);
QuickSort(a,0,siz-1);
int i=0,j=11;
printArr(a,siz);
system("pause");
void InputArray(int*a,int s)
for(int i=0; i<s; i++)
cout<<"ELement ["<<i<<"] = "; cin>>a[i];
void QuickSort(int *a,int start,int end)
if(start<end)
int pivot=partition(a,start,end);
QuickSort(a,start,pivot);
QuickSort(a,pivot+1,end);
int partition(int *a,int start,int end)
int currentPivotValue=a[start];
int i=start-1, j=end+1;
while(true)
i++;
while(i<j && a[i]<currentPivotValue) i++;
j--;
while(j>start && a[j]>currentPivotValue) j--;
if(i<j) swap(a,i,j);
else return j;
void swap(int *b,int i,int j)
int t=b[i];
b[i]=b[j];
b[j]=t;
void printArr(int *a,int Siz)
for(int i=0; i<Siz; i++) cout<<a[i]<<" ";
【讨论】:
以上是关于具有重复键的快速排序算法的主要内容,如果未能解决你的问题,请参考以下文章