快速排序 (Quicksort)
问题
从小到大排序序列 [l, r]
思路
取序列中一值 [p], 称为主元 (pivot element)
将序列分为 [l, p-1], [p+1, r], 且 [l, p-1] 序列中所有的值都小于或等于 [p+1, r]
递归处理这两个子序列
比较复杂的部分是按规则将主序列分成两个子序列,称为 Partition 过程
对于 [l, r-1] 序列,将 [r] 作为主元,i, j 用于标记
i 用于在 [l, r-1] 中划分小于和大于 [r] 的分界,
精确点说就是,[l, i-1] 中的所有值小于等于 [r],
[i, r-1] 中的所有值大于等于 [r]
j 用于每次比较
概括一下思想就是:j 从 l 增加到 r-1, 每次将 [j] 与 [r] 比较,如果 [j] 小于 [r],
那么 i++ (小于 [r] 的值又多了一个), 交换 [j] 和 [i](使 [l, i-1] 中的所有值都小于等于 [r])
代码如下:
(define (partition vec l r)
(let ([pivot-value (vector-ref vec r)])
(define (iter i j)
(if (< j r)
(if (< (vector-ref vec j) pivot-value)
(begin
(vector-swap! vec i j)
(iter (+ i 1) (+ j 1)))
(iter i (+ j 1)))
(begin
(vector-swap! vec i r)
i)))
(iter l l)))
C 语言版:
int partition(int arr[], int l, int r)
{
int i, j;
int pivot_value = arr[r];
for (i = l, j = l; j < r; j++) {
if (arr[j] < pivot_value) {
swap(arr, i, j);
i++;
}
}
swap(arr, i, j);
return i;
}
代码
(define (quick-sort vec l r)
(if (< l r)
(let ([p (partition vec l r)])
(quick-sort vec l (- p 1))
(quick-sort vec (+ p 1) r))
'()))