Python实现的数据结构与算法之快速排序详解


Posted in Python onApril 22, 2015

本文实例讲述了Python实现的数据结构与算法之快速排序。分享给大家供大家参考。具体分析如下:

一、概述

快速排序(quick sort)是一种分治排序算法。该算法首先 选取 一个划分元素(partition element,有时又称为pivot);接着重排列表将其 划分 为三个部分:left(小于划分元素pivot的部分)、划分元素pivot、right(大于划分元素pivot的部分),此时,划分元素pivot已经在列表的最终位置上;然后分别对left和right两个部分进行 递归排序

其中,划分元素的 选取 直接影响到快速排序算法的效率,通常选择列表的第一个元素或者中间元素或者最后一个元素作为划分元素,当然也有更复杂的选择方式;划分 过程根据划分元素重排列表,是快速排序算法的关键所在,该过程的原理示意图如下:

<-- 选取划分元素 -->

Python实现的数据结构与算法之快速排序详解

<-- 划分过程 -->

Python实现的数据结构与算法之快速排序详解

<-- 划分结果 -->

Python实现的数据结构与算法之快速排序详解

快速排序算法的优点是:原位排序(只使用很小的辅助栈),平均情况下的时间复杂度为 O(n log n)。快速排序算法的缺点是:它是不稳定的排序算法,最坏情况下的时间复杂度为 O(n2)。

二、Python实现

1、标准实现

#!/usr/bin/env python
# -*- coding: utf-8 -*-
def stdQuicksort(L):
  qsort(L, 0, len(L) - 1)
def qsort(L, first, last):
  if first < last:
    split = partition(L, first, last)
    qsort(L, first, split - 1)
    qsort(L, split + 1, last)
def partition(L, first, last):
  # 选取列表中的第一个元素作为划分元素
  pivot = L[first]
  leftmark = first + 1
  rightmark = last
  while True:
    while L[leftmark] <= pivot: 
 # 如果列表中存在与划分元素pivot相等的元素,让它位于left部分
     # 以下检测用于划分元素pivot是列表中的最大元素时,
  #防止leftmark越界
      if leftmark == rightmark:
        break
      leftmark += 1
    while L[rightmark] > pivot:
      # 这里不需要检测,划分元素pivot是列表中的最小元素时,
      # rightmark会自动停在first处
      rightmark -= 1
    if leftmark < rightmark:
      # 此时,leftmark处的元素大于pivot,
   #而rightmark处的元素小于等于pivot,交换二者
      L[leftmark], L[rightmark] = L[rightmark], L[leftmark]
    else:
      break
  # 交换first处的划分元素与rightmark处的元素
  L[first], L[rightmark] = L[rightmark], L[first]
  # 返回划分元素pivot的最终位置
  return rightmark

2、Pythonic实现

#!/usr/bin/env python
# -*- coding: utf-8 -*-
def pycQuicksort(L):
  if len(L) <= 1: return L
  return pycQuicksort([x for x in L if x < L[0]]) + \
      [x for x in L if x == L[0]] + \
      pycQuicksort([x for x in L if x > L[0]])

对比 标准实现 可以看出,Pythonic实现 更简洁、更直观、更酷。但需要指出的是,Pythonic实现 使用了Python中的 列表解析 (List Comprehension,也叫列表展开、列表推导),每一次 递归排序 都会产生新的列表,因此失去了快速排序算法本来的 原位排序 的优点。

三、算法测试

#!/usr/bin/env python
# -*- coding: utf-8 -*-
if __name__ == '__main__':
  L = [54, 26, 93, 17, 77, 31, 44, 55, 20]
  M = L[:]
  print('before stdQuicksort: ' + str(L))
  stdQuicksort(L)
  print('after stdQuicksort: ' + str(L))
  print('before pycQuicksort: ' + str(M))
  print('after pycQuicksort: ' + str(pycQuicksort(M)))

运行结果:

$ python testquicksort.py
before stdQuicksort: [54, 26, 93, 17, 77, 31, 44, 55, 20]
after stdQuicksort: [17, 20, 26, 31, 44, 54, 55, 77, 93]
before pycQuicksort: [54, 26, 93, 17, 77, 31, 44, 55, 20]
after pycQuicksort: [17, 20, 26, 31, 44, 54, 55, 77, 93]

希望本文所述对大家的Python程序设计有所帮助。

Python 相关文章推荐
Python中的装饰器用法详解
Jan 14 Python
Python机器学习之决策树算法
Dec 22 Python
python字典快速保存于读取的方法
Mar 23 Python
解决PyCharm不运行脚本,而是运行单元测试的问题
Jan 17 Python
Django使用redis缓存服务器的实现代码示例
Apr 28 Python
Pytorch反向求导更新网络参数的方法
Aug 17 Python
python 字典套字典或列表的示例
Dec 16 Python
Python多线程Threading、子线程与守护线程实例详解
Mar 24 Python
keras 两种训练模型方式详解fit和fit_generator(节省内存)
Jul 03 Python
python 实现的IP 存活扫描脚本
Dec 10 Python
python中altair可视化库实例用法
Jan 26 Python
python爬取股票最新数据并用excel绘制树状图的示例
Mar 01 Python
利用Fn.py库在Python中进行函数式编程
Apr 22 #Python
Python实现的数据结构与算法之基本搜索详解
Apr 22 #Python
Python实现的数据结构与算法之链表详解
Apr 22 #Python
Python实现的数据结构与算法之双端队列详解
Apr 22 #Python
Python实现的数据结构与算法之队列详解
Apr 22 #Python
详尽讲述用Python的Django框架测试驱动开发的教程
Apr 22 #Python
Hadoop中的Python框架的使用指南
Apr 22 #Python
You might like
PHP实现懒加载的方法
2015/03/07 PHP
PHP实现用户异地登录提醒功能的方法【基于thinkPHP框架】
2018/03/15 PHP
Laravel 解决419错误 -ajax请求错误的问题(CSRF验证)
2019/10/25 PHP
基于Web标准的UI组件 — 树状菜单(2)
2006/09/18 Javascript
从jQuery.camelCase()学习string.replace() 函数学习
2011/09/13 Javascript
JS获取CSS样式(style/getComputedStyle/currentStyle)
2016/01/19 Javascript
jQuery 监控键盘一段时间没输入
2016/04/22 Javascript
AngularJS基础 ng-mouseenter 指令示例代码
2016/08/02 Javascript
解析利用javascript如何判断一个数为素数
2016/12/08 Javascript
Easyui笔记2:实现datagrid多行删除的示例代码
2017/01/14 Javascript
JavaScript数据结构之链表的实现
2017/03/19 Javascript
微信小程序实现图片轮播及文件上传
2017/04/07 Javascript
js中Array对象的常用遍历方法详解
2019/01/17 Javascript
页面内锚点定位及跳转方法总结(推荐)
2019/04/24 Javascript
Vue 嵌套路由使用总结(推荐)
2020/01/13 Javascript
vue 使用lodash实现对象数组深拷贝操作
2020/09/10 Javascript
[01:05:56]2018DOTA2亚洲邀请赛3月29日 小组赛A组 Newbee VS VG
2018/03/30 DOTA
[01:11:46]DOTA2-DPC中国联赛 正赛 iG vs Magma BO3 第一场 2月23日
2021/03/11 DOTA
举例讲解Python设计模式编程的代理模式与抽象工厂模式
2016/01/16 Python
Python随机生成均匀分布在单位圆内的点代码示例
2017/11/13 Python
Django REST为文件属性输出完整URL的方法
2017/12/18 Python
Python中的CSV文件使用&quot;with&quot;语句的方式详解
2018/10/16 Python
Python常用爬虫代码总结方便查询
2019/02/25 Python
Python实现九宫格式的朋友圈功能内附“马云”朋友圈
2019/05/07 Python
selenium中get_cookies()和add_cookie()的用法详解
2020/01/06 Python
Python爬虫获取页面所有URL链接过程详解
2020/06/04 Python
Python3以GitHub为例来实现模拟登录和爬取的实例讲解
2020/07/30 Python
Python 保存加载mat格式文件的示例代码
2020/08/04 Python
Python 多进程原理及实现
2020/12/21 Python
python3判断IP地址的方法
2021/03/04 Python
澳大利亚儿童和婴儿产品在线商店:Lime Tree Kids
2017/10/05 全球购物
创先争优承诺书范文
2014/03/31 职场文书
2014年教师党员自我评议
2014/09/19 职场文书
党员个人对照检查材料范文
2014/09/24 职场文书
《改造我们的学习》心得体会
2014/11/07 职场文书
Python可视化神器pyecharts之绘制箱形图
2022/07/07 Python