快速排序的基本思路如下:
随便在数组里找一个数作为基准 , 把比基准大的数放在基准的后边 , 把比基准小的放在基准前面 .
通过这种方式 , 可以把这个排序算法的平均复杂度保持在O(n*lg(n)) .
下面介绍左右指针法实现快速排序 :
假设我们有一个数组 a[8] 如下:
我们要做的事情是:
1.定义两个数字 i 和 j , 分别让 i 和 j 等于数组元素下标的第一位和最后一位 .
2.在数组里随便选一个数 , 不妨假设这个数就是数组的第一个元素 .把这个数用key代替
3.当 a[j] 的值比key的值大的时候 , 我们让 j 指向前一个数组元素 , 一直到 找到一个比key小的元素为止 .
4.当 a[i] 的值比key的值小的时候 , 我们让 i 指向后一个数组元素 , 一直到 找到一个比key大的元素为止 .
5.做完这些之后,我们把a[i] 和a[j] 交换 .
6.只要 i 和 j 指向的元素不是同一个, 我们就一直执行步骤 3 4 5 .
请你拿出纸笔 , 看看每次按照我步骤 , 结果和我的一样吗 ? 千万不要偷懒啊 ! 手过一遍很重要
做完这些可以发现 a[i] = a[j] = 3 , 即 i 和 j 同时指向了 3
我们把刚才指定的 key 即 a[0] 与 a[i] 交换 , 得到数组
3 2 6 15 13 9 7 6
然后我们把key之前的数字分成一个数组 , 把 key之后的数字分成一个数组
3 2 6
15 13 9 7 6
然后对这两个新的数组继续使用刚才的方法 , 直到把数组分的只有一个元素为止 . 这一步显然可以用递归实现 .
具体代码如下 :
#include <stdio.h>
#include <stdlib.h>
int a[100];
void quickSort(int a[] , int start , int end)
{
int i = start+1 , j = end ;
int temp ;
int key = a[start];
if(start >= end)
return;
while(i != j)
{
while( i < j && a[j] > key)
j--;
while( i < j && a[i] < key)
i++;
if(i < j )
{
temp = a[i];
a[i] = a[j];
a[j] = temp;
}
}
temp = a[start];
a[start] = a[i];
a[i] = key;
quickSort(a , start , i - 1);
quickSort(a , i+1 , end );
}
int main(int argc, char *argv[]) {
int i,n;
scanf("%d",&n);
for(i = 0 ; i < n; i++)
scanf("%d", &a[i]);
quickSort(a , 0 , n-1);
for(i = 0; i < n ; i++)
printf("%d ", a[i]);
return 0;
}