上期文章排序算法——(2)Python实现十大常用排序算法为大家介绍了十大常用排序算法的前五种(冒泡、选择、插入、希尔、归并),因为快速排序的重要性,所以今天将单独为大家介绍一下快速排序!

一、算法介绍

排序算法(Sorting algorithm)是计算机科学最古老、最基本的课题之一。要想成为合格的程序员,就必须理解和掌握各种排序算法。其中"快速排序"(Quicksort)使用得最广泛,速度也较快。它是图灵奖得主C. A. R. Hoare(托尼·霍尔)于1960时提出来的。

二、算法原理

快排的实现方式多种多样,猪哥给大家写一种容易理解的:分治+迭代,只需要三步:

  1. 在数列之中,选择一个元素作为"基准"(pivot),或者叫比较值。
  2. 数列中所有元素都和这个基准值进行比较,如果比基准值小就移到基准值的左边,如果比基准值大就移到基准值的右边
  3. 以基准值左右两边的子列作为新数列,不断重复第一步和第二步,直到所有子集只剩下一个元素为止。

举个例子,假设我现在有一个数列需要使用快排来排序:{3, 44, 38, 5, 47, 15, 36, 26, 27, 2, 46, 4, 19, 50, 48},我们来看看使用快排的详细步骤:

  1. 选取中间的26作为基准值(基准值可以随便选)
  2. 数列从第一个元素3开始和基准值26进行比较,小于基准值,那么将它放入左边的分区中,第二个元素44比基准值26大,把它放入右边的分区中,依次类推就得到下图中的第二列。
  3. 然后依次对左右两个分区进行再分区,得到下图中的第三列,依次往下,直到最后只有一个元素
  4. 分解完成再一层一层返回,返回规则是:左边分区+基准值+右边分区

三、代码实现

quick_sort = lambda array: array if len(array) <= 1 else quick_sort([item for item in array[1:] if item <= array[0]]) + [array[0]] + quick_sort([item for item in array[1:] if item > array[0]])

是不是很简洁很秀,如果再有面试官让你手写一个快排,你就把这行写上去吧,面试官见了都要喊你秀儿,哈哈。

在你感叹python吊炸天的同时,你因该考虑到代码的可读性问题,lambda函数设计是为了代码的简洁性,但是滥用的话会导致可读性变得极差,而且现在pep8代码规范中也不建议使用lambda函数了,建议使用关键字def去定义一个函数,所以下面猪哥给大家写一段符合pythonic风格的快排代码

def quick_sort(arr):"""快速排序"""if len(arr) < 2:return arr# 选取基准,随便选哪个都可以,选中间的便于理解mid = arr[len(arr) // 2]# 定义基准值左右两个数列left, right = [], []# 从原始数组中移除基准值arr.remove(mid)for item in arr:# 大于基准值放右边if item >= mid:right.append(item)else:# 小于基准值放左边left.append(item)# 使用迭代进行比较return quick_sort(left) + [mid] + quick_sort(right)

四、算法分析

  1. 稳定性:快排是一种不稳定排序,比如基准值的前后都存在与基准值相同的元素,那么相同值就会被放在一边,这样就打乱了之前的相对顺序
  2. 比较性:因为排序时元素之间需要比较,所以是比较排序
  3. 时间复杂度:快排的时间复杂度为O(nlogn)
  4. 空间复杂度:排序时需要另外申请空间,并且随着数列规模增大而增大,其复杂度为:O(nlogn)
  5. 归并排序与快排 :归并排序与快排两种排序思想都是分而治之,但是它们分解和合并的策略不一样:归并是从中间直接将数列分成两个,而快排是比较后将小的放左边大的放右边,所以在合并的时候归并排序还是需要将两个数列重新再次排序,而快排则是直接合并不再需要排序,所以快排比归并排序更高效一些,可以从示意图中比较二者之间的区别。

五、快排优化

快速排序有一个缺点就是对于小规模的数据集性能不是很好。可能有人认为可以忽略这个缺点不计,因为大多数排序都只要考虑大规模的适应性就行了。但是快速排序算法使用了分治技术,最终来说大的数据集都要分为小的数据集来进行处理,所以快排分解到最后几层性能不是很好,所以我们就可以使用扬长避短的策略去优化快排:

  1. 先使用快排对数据集进行排序,此时的数据集已经达到了基本有序的状态
  2. 然后当分区的规模达到一定小时,便停止快速排序算法,而是改用插入排序,因为我们之前讲过插入排序在对基本有序的数据集排序有着接近线性的复杂度,性能比较好。

这一改进被证明比持续使用快速排序算法要有效的多。

六、模拟面试

  • 面试官:你了解快排吗?
  • 你:略知一二
  • 面试官:那你讲讲快排的算法思想吧
  • 你:快排基本思想是:从数据集中选取一个基准,然后让数据集的每个元素和基准值比较,小于基准值的元素放入左边分区大于基准值的元素放入右边分区,最后以左右两边分区为新的数据集进行递归分区,直到只剩一个元素。
  • 面试官:快排有什么优点,有什么缺点?
  • 你:分治思想的排序在处理大数据集量时效果比较好,小数据集性能差些。
  • 面试官:那该如何优化?
  • 你:对大规模数据集进行快排,当分区的规模达到一定小时改用插入排序,插入排序在小数据规模时排序性能较好。
  • 面试官:那你能手写一个快排吗?
  • 你:
quick_sort = lambda array: array if len(array) <= 1 else quick_sort([item for item in array[1:] if item <= array[0]]) + [array[0]] + quick_sort([item for item in array[1:] if item > array[0]])

  

七、总结

快排是面试与考试中最高频的一种排序算法(没有之一),请大家务必理解与掌握,欢迎大家在评论区留言,同时也希望大家转发分享让更多的人爱上python这门语言。

转载于:https://www.cnblogs.com/pig66/p/10618035.html

Python一行代码实现快速排序相关推荐

  1. 链表快速排序python_Python一行代码实现快速排序的方法

    今天将单独为大家介绍一下快速排序! 一.算法介绍 排序算法(Sorting algorithm)是计算机科学最古老.最基本的课题之一.要想成为合格的程序员,就必须理解和掌握各种排序算法.其中" ...

  2. 【Python】Python一行代码能做什么,30个实用案例代码详解

    Python语法简洁,能够用一行代码实现很多有趣的功能,这次来整理30个常见的Python一行代码集合. 1.转置矩阵 old_list = [[1, 2, 3], [3, 4, 6], [5, 6, ...

  3. 50 条有趣的 Python 一行代码

    在学习Python的过程中,总会发现Python能够轻易的解决许多问题. 一些复杂的任务,甚至可以使用一行Python代码就能搞定. 下面给大家介绍50个有趣的Python一行代码,都很实用. 希望大 ...

  4. 50条有趣的Python一行代码

    公众号后台回复"图书",了解更多号主新书内容 作者:小F 来源:法纳斯特 在学习Python的过程中,总会发现Python能够轻易的解决许多问题. 一些复杂的任务,甚至可以使用一行 ...

  5. 50条有趣的Python一行代码,建议收藏!

    大家好,我是小F. 在学习Python的过程中,总会发现Python能够轻易的解决许多问题. 一些复杂的任务,甚至可以使用一行Python代码就能搞定. 下面,小F给大家介绍50个有趣的Python一 ...

  6. 学习必备的50条非常有趣且实用的Python一行代码,值得收藏

    前言 学习必备的50条非常有趣且实用的Python一行代码,值得收藏! 让我们愉快地开始吧~编程学习资料免费点击 开发工具 Python版本: 3.6.4 相关模块: 环境搭建 安装Python并添加 ...

  7. Python一行代码能做什么,30个实用案例代码详解

    Python语法简洁,能够用一行代码实现很多有趣的功能,这次来整理30个常见的Python一行代码集合. 1.转置矩阵 old_list = [[1, 2, 3], [3, 4, 6], [5, 6, ...

  8. 【第76期】50条有趣的Python一行代码,建议收藏!

    在学习Python的过程中,总会发现Python能够轻易的解决许多问题. 一些复杂的任务,甚至可以使用一行Python代码就能搞定. 下面,小F给大家介绍50个有趣的Python一行代码,都很实用. ...

  9. python代码大全p-【python】10分钟教你用python一行代码搞点大新闻

    准备 相信各位对python的语言简洁已经深有领会了.那么,今天就带大家一探究竟.看看一行python代码究竟能干些什么大新闻.赶紧抄起手中的家伙,跟我来试试吧. 首先你得先在命令行进入python. ...

最新文章

  1. C++_重载new,delete
  2. windows-服务端口
  3. 用了虚拟机Linux不能上网,虚拟机Linux不能上网怎么办
  4. Nginx+Tomcat+Memcached集群 【测试成功】
  5. 开课吧:Java开发常用技术基础部分有哪些?
  6. 那些精贵的3D视觉系统学习资源总结(附书籍、网址与视频教程)
  7. 181008有道扇贝每日一句
  8. 不容错过!Greenplum的又一本好书
  9. 如何高效绘制知识地图?
  10. 长期在计算机房内会有多大辐射,机房辐射范围和预防辐射?计算机房里面适用的屏蔽隔离防辐射材料是什么?...
  11. java表白小程序_c语言表白小程序代码创意
  12. 战略规划,要这么做才对!
  13. Python编写的com组件大全与解决对策
  14. 基于vue3+ts+scss的后台管理系统(二)----excel的导入导出
  15. iphone传输 android,安卓苹果数据互传,三种方法教你怎样把iPhone数据迁移到安卓手机...
  16. 基于java的奖学金评定系统设计与实现
  17. 计算机软件著作权的注册和认证
  18. php 图片生成视频,PHP基于ffmpeg实现转换视频,截图及生成缩略图的方法
  19. 中国田联要求:刘翔和王军霞生个孩子!
  20. 营销-营销方式:营销方式

热门文章

  1. js添加菜单栏之后停留在那里
  2. Cesium 创建Geometry
  3. 矩阵-----对称矩阵及其压缩存储稀疏矩阵
  4. Linux下如何把时间转成秒数,或把秒数转换成标准时间
  5. 批量导入导出站点权限site permissions
  6. android开发4:Android布局管理器1(线性布局,相对布局RelativeLayout-案例)
  7. 手动安装oracle软件 删软件
  8. uchome 模板引擎
  9. Linux退出vi编辑
  10. vue 使用font-awesome 只需两步