快速排序算法_全面解析十大排序算法之六:快速排序

a4718c18485e6aa1a38d3bf96d825937.png 

点击上方蓝字关注我们吧

c70a634791628bb3c7bfc1e2d931a93b.png

1. 十种排序算法的复杂度和稳定性

d67d84b2b5195834967827156dab6f9c.png

278cf649e5fad356f3c6c5c1897e0c25.png 278cf649e5fad356f3c6c5c1897e0c25.png

时间复杂度:一个算法消耗所需要的时间

空间复杂度:运行一个算法所需要的内存时间

稳定性:如一个排列数组:1、4、5、6、4、7. 此时有一对相等的数字 4 ,设前面的4为 a4,后一个4 为 b4。 如果排序之后 a4 仍然在 b4 前面,则表示此种算法排序是具有稳定性的;如果排序之后 a4 在 b4 后面,则表示是 不稳定性的。

278cf649e5fad356f3c6c5c1897e0c25.png 278cf649e5fad356f3c6c5c1897e0c25.png

2. 什么是快速排序算法

快速排序的基本思想:通过设定一个基准值,在进行一趟排序后将待排记录分隔成独立的两部分,以基准值为界限,其中一部分记录的值均比另一部分的值小,则可分别递归对这两部分记录继续进行排序,以达到整个序列有序。

递归算法讲解参考

3. 算法运行过程

算法运行过程视频演示

快速排序算法的运作如下:

  • 从数列中挑出一个元素,称为"基准"(一般是去数组中的第一个元素),

  • 重新排序数列,所有比基准值小的元素摆放在基准前面,所有比基准值大的元素摆在基准后面(相同的数可以到任何一边)。在这个分区结束之后,该基准就处于数列的中间位置。这个称为分区(partition)操作。

  • 递归地(recursively)把小于基准值元素的子数列和大于基准值元素的子数列排序。

    看图说明,更清晰:

    a1747cb427fed045bee5491edadcf87b.png

4. 代码实现

Python实现

#4.快速排序#将一个数组分为2 个数组, 在通过递归调用自身函数为每一个子数组进行排序def quick_sort(alist, start, end):    if start >= end:        return  #递归的退出条件,直接退出函数    low = start # 由左向右移动    high = end     mid = alist[low]    #设置第一个元素为基准元素, 小于它的再左边,大于它的在右边        while high > low:        while high > low and alist[high] >= mid:    #需要有个等号最后判断条件停止,使得其光标往左移动             high -= 1        alist[low] = alist[high]                while high > low and alist[low] < mid:  #往右移动            low += 1        alist[high] = alist[low]            alist[low] = mid #最后将基准赋值        quick_sort(alist, start, low -1)    #进行递归, 以low为标注分界    quick_sort(alist, low+1, end)    return alistn =len(li)print('test quick sort')print(quick_sort(li, 0, n-1))

Java实现

public static void quickSort(int[] arr){    qsort(arr, 0, arr.length-1);}private static void qsort(int[] arr, int low, int high){    if (low >= high)        return;    int pivot = partition(arr, low, high);        //将数组分为两部分    qsort(arr, low, pivot-1);                   //递归排序左子数组    qsort(arr, pivot+1, high);                  //递归排序右子数组}private static int partition(int[] arr, int low, int high){    int pivot = arr[low];     //基准    while (low < high){        while (low < high && arr[high] >= pivot) --high;        arr[low]=arr[high];             //交换比基准大的记录到左端        while (low < high && arr[low] <= pivot) ++low;        arr[high] = arr[low];           //交换比基准小的记录到右端    }    //扫描完成,基准到位    arr[low] = pivot;    //返回的是基准的位置    return low;}

C++实现

int QKPass(int r[], int left, int right){  int low = left;  int high = right;  r[0] = r[left];  while (low < high)  {    while (low < high && r[high] > r[0])    {      high--;    }    if (low < high)    {      r[low] = r[high];      low++;    }    while (low < high && r[low] < r[0])    {      low++;    }    if (low < high)    {      r[high] = r[low];      high--;    }  }  r[low] = r[0];  return low;}void QKSort(int r[], int low,int high){  if (low < high)  {    int pos = QKPass(r,low,high);    QKSort(r, low, pos - 1);    QKSort(r, pos + 1, high);  }}

快速排序的名字起的是简单粗暴,因为一听到这个名字你就知道它存在的意义,就是快,而且效率高!

它是处理大数据最快的排序算法之一了。虽然最差的时间复杂度达到了 O(n²)【这是在数组有序的情况下】,但是人家就是优秀,在大多数情况下都比平均时间复杂度为 O(n logn) 的排序算法表现要更好。

快速排序的最坏运行情况是 O(n²),比如说顺序数列的快排。但它的平摊期望时间是 O(nlogn),且 O(nlogn) 记号中隐含的常数因子很小,比复杂度稳定等于 O(nlogn) 的归并排序要小很多。所以,对绝大多数顺序性较弱的随机数列而言,快速排序总是优于归并排序。

END

7dd88f03d238dd5f49fc37166f9e920e.png

扫描关注我们

免费分享程序员面经、机器学习、编程语言等,

1300G互联网视频、书籍资源,各种干货。

生活不止于编程,爱编程更爱生活。

decdfce47495ff5239d0bdf19c0e856a.png 46a37537880258b8f2b0167d803393cb.png

文章好看点这里

a618181eadd6893cf3754d15f13d6996.gif
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值