快速排序是一种常见的排序算法,大多数情况下快速排序都是最快的。快速排序本质上是将一个数组划分一个子数组(关于划分前面已经说过),递归调用自身为每一个子数组进行快速排序。
快速排序的过程:以数组为例,针对数组进行排序。
1 把数组或者子数组划分为左边(比关键字小的)一组和右边比关键字大的一组。
2 调用自身对左边一组进行排序。
3 再次调用自身对右边的一组进行排序。
4 不断递归循环以上步骤,子数组长度不断缩短。最终通过不断划分数组的方式直到限制一个数据项时返回,这也是递归的基值条件。
快速排序针对每个子数组使用的是关键字排序。这里的关键字可以使用每个子数组的最右端数据项。在划分的基础上需要添加一个步骤就是在交换双边数据时还需要交换关键字与数据划分位置。以下图表示这个过程:
![这里写图片描述](https://img-blog.csdn.net/20160916221857885)
采用递归实现快速排序,下图表示以上几个步骤:
![这里写图片描述](https://img-blog.csdn.net/20160916222020783)
第一次进行划分,划分两个子数组,通过交换数据项和关键字,可以得到下图:
![这里写图片描述](https://img-blog.csdn.net/20160916222202718)
初次以数组最右端为关键字(这里是数据项18),以18为划分项,左右两边进行子数组递归再进行划分和交换操作。
![这里写图片描述](https://img-blog.csdn.net/20160916222546880)
接下来就是独自对两个子数组进行递归划分交换即可;
![这里写图片描述](https://img-blog.csdn.net/20160916222836365)
继续递归,条件判断,不断划分子数组,不断交换关键字。
![这里写图片描述](https://img-blog.csdn.net/20160916223002100)
关键字12左端已经是有序不需要交换,右端已经是一个数据项此次递归return,结合其他子数组的划分情况。此时综合就是一个有序数组。
![这里写图片描述](https://img-blog.csdn.net/20160916223224852)
以下是快速排序的递归代码:
public void quickSort(int left,int right)
{
if(right-left<=0)
return;
else
{
int temp=array[right];
int partion=divide(left,right,temp);
quickSort(left, partion-1);
quickSort(partion+1, right);
}
}
以下是划分算法,相比较之前的划分算法这里的关键字是需要指定的,这里以每个子数组的最右端数据项为关键字。
public int divide(int left,int right,int actionNum)
{
int leftPtr=left-1;
int rightPrt=right;
while(true)
{
while(array[++leftPtr]<actionNum)
{
;
}
while(rightPrt>0&&array[--rightPrt]>actionNum)
{
;
}
if(leftPtr>=rightPrt)
{
break;
}
else
{
swap(leftPtr,rightPrt);
}
}
swap(leftPtr,right);
return leftPtr;
数据交换,一个划分过程中出现的左右子数组数据交换,另外一个是关键字的交换。
public void swap(int left,int right)
{
int temp=0;
temp=array[left];
array[left]=array[right];
array[right]=temp;
}
public void showArray()
{
for(int i=0;i<array.length;i++)
{
System.out.print(array[i]+" ");
}
System.out.println("");
}
随机数组的创建
private int[] array=null;
public QuickSort(int n)
{
array=new int[n];
for(int i=0;i<n;i++)
{
int a=(int)(Math.random()*100);
array[i]=a;
}
System.out.println("排序之前:");
showArray();
}
public void quick()
{
quickSort(0,array.length-1);
}
测试与结果:
QuickSort quickDemo=new QuickSort(18);
quickDemo.quick();
System.out.println("排序之后");
quickDemo.showArray();
排序之前:
74 92 61 12 36 33 38 31 25 69 42 76 81 95 37 67 80 41
排序之后
12 25 31 33 36 37 38 41 42 61 67 69 74 76 80 81 92 95
快速排序的效率
快速排序的时间复杂度为O(N*log(N))。快速排序采用的是分治思想,快速排序比一般排序要快,效率较高。