快速排序

快速排序同归并排序一样,也采用的是分治策略。快速排序最终要的步骤是划分子数组,假设有个数组A[p..r]被划分成两个子数组(可能为空)A[p..q-1]和A[q+1..r],使得A[p..q-1]中的每个元素都小于等于A[q],且A[q]小于等于A[q+1..r]中的每个元素。划分过程伪代码如下:

PARTITION(A, p, r)
    x <-- A[r]
    i <-- p-1
    for j <-- p to r-1
        do if A[j] <= x
            then i <-- i+1
                exchange A[i] <--> A[j]
    exchange A[i+1] <--> A[r]
    return i+1

此过程的c程序如下:

int partition(int A[], int p, int r)
{
	int i, j;
	int x;

	x = A[r];
	i = p-1;

	for (j = p; j < r; j++) {
		if (A[j] <= x) {
			swap(&A[++i], &A[j]);
		}
	}

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

	return i+1;
}

快速排序伪代码如下:

QUICKSORT(A, p, r)
    if p < r
        then q <-- PARTITION(A, p, r)
            QUICKSORT(A, p, q-1)
            QUICKSORT(A, q+1, r)

c程序如下:

void quick_sort(int A[], int p, int r)
{
	int q;

	if (p < r) {
		q = partition(A, p, r);
		quick_sort(A, p, q-1);
		quick_sort(A, q+1, r);
	}
}



例如数组{2, 8, 7, 1, 3, 5, 6, 4},排序过程是这样的:
(1)    2 8 7 1 3 5 6 4(主元)

(2)    2 1 3 4 7 5 6 8
x为主元r,i为-1,j初值为0,因为A[0]为2小于x,所以i加1之后为0,然后交换A[0]和A[0]的值,因为相同所以原数组不变。i不变,j++到3,此时A[3]为1小于x,i加1之后为1,交换A[1]和A[3]的值,原数组变为2 1 7 8 3 5 6 4。j++到4,再交换A[2]和A[4]的值,交换后数组为2 1 3 8 7 5 6 4。j++,后面没有比x再小的数,所以for循环结束,再交换A[3]和A[7]的值,数组变为2 1 3 4 7 5 6 8,并返回3。

(3)    1 2 3 4 7 5 6 8
这样数组A被划分成了两个数组{2, 1, 3}和{7, 5, 6, 8},然后再对这两个数组进行快速排序。{2, 1, 3}数组主元为3,首先是2和2互换不变,1和1互换不变,最后3与3互换不变,这样{2, 1, 3}数组再分成两个数组{2, 1}和{3}。再对{2, 1}数组进行排序,变为{1, 2}。

{4}    1 2 3 4 5 6 7 8
再对数组{7, 5, 6, 8}进行排序,再分成两个数组{7, 5, 6}和{8},{7, 5, 6}数组排序之后变为{5, 6, 7}。

最后,完整程序如下:

#include <stdio.h>

void dump(int a[], int len)
{
	int i;

	for (i = 0; i < len; i++) {
		printf("%3d", a[i]);
	}
	printf("
");
}

void swap(int *a, int *b)
{
	int tmp;

	tmp = *a;
	*a = *b;
	*b = tmp;
}

int partition(int A[], int p, int r)
{
	int i, j;
	int x;

	x = A[r];
	i = p-1;

	for (j = p; j < r; j++) {
		if (A[j] <= x) {
			swap(&A[++i], &A[j]);
		}
	}

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

	return i+1;
}

void quick_sort(int A[], int p, int r)
{
	int q;

	if (p < r) {
		q = partition(A, p, r);
		quick_sort(A, p, q-1);
		quick_sort(A, q+1, r);
	}
}

int main(void)
{
	int a[] = {2, 8, 7, 1, 3, 5, 6, 4};

	int len = sizeof(a) / sizeof(a[0]);

	dump(a, len);

	quick_sort(a, 0, len-1);

	dump(a, len);

	return 0;
}
原文地址:https://www.cnblogs.com/keanuyaoo/p/3283368.html