思想:分治法
从数组中选取一个pivot(基准)
将数组分为两部分,比基准小的放在基准左边,比基准大放在基准右边(分区)。然后继续对左右两部分做同样处理(递归)。
以下给出两种partition思路
partition1:
int partition(int *a, int left, int right, int pivotIndex) {
int pivotValue = a[pivotIndex];
int storeIndex = left;//代表左部分的长度,同时也是右部分首下标
swap(a[pivotIndex], a[right]);
for(int i = left; i < right; i++) {
if(a[i] < pivotValue) {//从左往右找到数组中比pivot小的值放到左部分最后一个
swap(a[i], a[storeIndex]);
storeIndex++;
}
}
swap(a[storeIndex], a[right]);
return storeIndex;
}
partition2:
int partition(int *a, int left, int right, int pivotIndex) {
int pivotValue = a[pivotIndex];
swap(a[pivotIndex], a[right]);
int i = left - 1,j = right;
for(;;) {
while(a[++i] < pivotValue);//从左往右找到下一个比pivot大的值
//即找左部分大的值
while(a[--j] > pivotValue);//从右往左找到下一个比pivot小的值
//即找右部分小的值
if(i < j)swap(a[i], a[j]);//交换使小的到左边,大的到右边
else break;
}
//因为i >= j时终止,所以最后的i为右部分的首index
swap(a[right], a[i]);
return i;
}
快速排序quicksort:
void q_sort(int *a, int left, int right) {
if(left >= right)return ;
int pivotIndex = left - (left - right)/2;//选取pivot
//可以采用其他选取方式,如随机选取
int new_pivotIndex = partition(a, left, right, pivotIndex);
q_sort(a, left, new_pivotIndex - 1);
q_sort(a,new_pivotIndex + 1, right);
}