对一个东西,首先要讲他的利与弊,才知道怎么使用它。快速排序适用于各类不一样的输入数据且在通常应用中比其余排序都要快得多。快速排序引人注目的特色包括它是原地排序(只须要一个很小的辅助栈),且长度为N的数组排序所需的时间和NlgN成正比。它的主要缺点是很是脆弱,在实现时要很是当心才能避免低劣的性能。java
有了对比,才能知道它的好处。其实快速排序是一种分治的排序算法。它将一个数组分红两个子数组,将两部分独立地排序。讲到这里,有人就会有个疑问,那不是和归并排序同样吗?合并排序也是分治算法的一种,也是将一个数组分红两个子数组。快速排序和归并排序时互补的:归并排序将数组分红两个子数组分别排序,并将有序的子数组归并以整个数组排序;而快速排序将数组排序的方式则是当两个数组都有序时整个数组也就天然有序了。在第一种状况下,递归调用发生在处理整个数组以前;在第二种状况下,递归调用发生在处理整个数组以后。在归并排序中,一个数组被等分为两半;在快速排序中,切分的位置取决于数组的内容。这句话最重要。算法
public class Quick{ public static void sort(Comparable[] a){ StdRandom.shuffle(a);//消除对输入的依赖,直接生成随机数 sort(a,0,a.length-1); } private static void sort(Comparable[] a, int lo, int hi){ if(hi <= lo) return; int j= partition(a,lo,hi);//切分 sort(a,lo,j-1); sort(a,j+1,hi); } private static int partition(Comparable[] a, int lo ,int hi){ int i = io,j=hi+1; Comparable v = a[lo]; while(true){ while(less(a[++i],v)) if(i==hi) break; while(less(v,a[--j])) if(j==lo) break; if(i>=j) break; exch(a,i,j) } exch(a,lo,j); return j; } private static void exch(Comparable[] a ,int i ,int j){ Comparable t = a[i];a[i]=a[j];a[j]=t; } private static boolean less(Comparable v , Comparable w){ return v.compareTo(w)<0; } }