【发布时间】:2016-02-17 00:58:15
【问题描述】:
对算法进行一些刷新。我写了这个快速排序实现:
#define SWAP(X, Y, Type) { Type Temp = (X); (X) = (Y); (Y) = Temp; }
int QSPartition(int* Array, int StartIndex, int EndIndex)
{
int PivotDestinationIndex = StartIndex;
int Pivot = Array[EndIndex];
for(int i = StartIndex; i <= EndIndex; i++)
{
if (Array[i] < Pivot)
{
SWAP(Array[i], Array[PivotDestinationIndex], int);
PivotDestinationIndex++;
}
}
SWAP(Array[PivotDestinationIndex], Array[EndIndex], int);
return PivotDestinationIndex;
}
void QuickSort(int* Array, int StartIndex, int EndIndex)
{
if (StartIndex >= EndIndex)
return;
int PivotIndex = QSPartition(Array, StartIndex, EndIndex);
QuickSort(Array, PivotIndex + 1, EndIndex);
QuickSort(Array, StartIndex, PivotIndex - 1);
}
在我的主程序中:
#define Measure(Iterations, What, Code)\
{\
clock_t Begin = clock();\
for(int _im_ = 0; _im_ < Iterations; _im_++)\
{\
Code;\
}\
clock_t End = clock();\
printf("Time took to " What ": %.1f ms\n", (double)(End - Begin));\
}
int CompareInt(const void* x, const void* y) { return *(int*)x - *(int*)y; }
int main()
{
srand(time(0));
int Count = 100000;
int* Array0 = (int*)malloc(sizeof(int) * Count);
int* Array1 = (int*)malloc(sizeof(int) * Count);
for (int i = 0; i < Count; i++)
{
int RandomValue = rand() % 100;
Array0[i] = RandomValue;
Array1[i] = RandomValue;
}
Measure(1, "My Quick", QuickSort(Array0, 0, Count - 1));
Measure(1, "C Quick", qsort(Array1, Count, sizeof(int), CompareInt));
getchar();
return 0;
}
输出是“My Quick”总是在 125 ms 附近,而“C Quick”总是在 25 ms 附近。 (32 位 DEBUG 构建 - 在 RELEASE 上仍然慢 5 倍)
发生了什么事?为什么我的实施速度较慢? (我尝试内联函数,但效果不大)还有其他问题吗? (我计时的方式,或者我用随机值填充数组的方式,或者......?)
【问题讨论】:
-
qsort 是一种快速排序。它不一定是快速排序的实现。
-
我没有得到反对票...
-
可能会有一些优化来使用一些手动编写的代码没有利用的 cpu 指令
-
在快速排序不太理想的情况下,许多 qsort 会切换到非快速排序算法。如果内存够用,当您的元素少于 16 个时,MSVC 将切换到堆排序。
-
我没有运行任何测试,但一个很大的不同是
qsort通常在大小较小时通过下拉到另一种排序来进行优化。您可以在 glibcqsortsource: 插入排序中看到它,当有 4 个或更少元素时。它也是迭代的,而不是递归的。
标签: c performance sorting quicksort