快速排序是用於排序的最佳使用選擇,這是由於其平均性能至關好,指望運行時間是O(nlgn),且記號中隱藏的常數因子很小。另外:它還可以進行就地排序。算法
快速排序是基於分治模型的:數組
void quicksort(int* A, int p, int r){ if (p < r) { int q = partition(A, p, r); quicksort(A, p, q); quicksort(A, q+1, r); } }
爲排序一個完整的數組A,最初的調用是quicksort(A, 0, __count_of(A) )dom
快排算法的關鍵是PARTITION過程,它對子數組A[p...r)進行就地重排 函數
int partition(int* A, int p, int r) { int x = A[r -1]; int i = p - 1; int j = p; for (; j < r-1; j++) { if (A[j] <=x) { i++; int tmp = A[i]; A[i] = A[j]; A[j] = tmp;// A[i] A[j] } } i++; int tmp = A[i]; A[i] = A[j]; A[j] = tmp;// A[i] A[j] return i; }
能夠用循環不變式來分析一下Partition程序:性能
循環不變量是.任何在[p,i]的數都小於等於x, 在[i,j)的數都大於x。 在[j,r)的數未知。 A[r-1] = X。ui
快排性能最差時是Θ(n2)spa
平均性能Θ(nlgn)code
快排的隨機化版本blog
int randomized-partition(int* A, int p, int r) { int i = random(p,r); int tmp = A[r-1]; A[r-1] = A[i]; A[i] = tmp; return partition(A, p, r); }
新的快速排序過程再也不調用partition,而是調用randomized-partition排序
void quicksort(int* A, int p, int r){ if (p < r) { int q = randomized-partition(A, p, r); quicksort(A, p, q); quicksort(A, q+1, r); } }
擴展:
快排除了算法導論的版本外,c語言的庫函數stdlib.h也提供了一個qsort函數。它的源代碼能夠從這裏下載http://www.gnu.org/software/libc/
代碼路徑在glibc-2.27/stdlib/qsort.c. 再也不累述。