python下实现二叉堆以及堆排序的示例


Posted in Python onSeptember 29, 2017

堆是一种特殊的树形结构, 堆中的数据存储满足一定的堆序。堆排序是一种选择排序, 其算法复杂度, 时间复杂度相对于其他的排序算法都有很大的优势。

堆分为大头堆和小头堆, 正如其名, 大头堆的第一个元素是最大的, 每个有子结点的父结点, 其数据值都比其子结点的值要大。小头堆则相反。

我大概讲解下建一个树形堆的算法过程:

找到N/2 位置的数组数据, 从这个位置开始, 找到该节点的左子结点的索引, 先比较这个结点的下的子结点, 找到最大的那个, 将最大的子结点的索引赋值给左子结点, 然后将最大的子结点和父结点进行对比, 如果比父结点大, 与父节点交换数据。当然, 我只是大概说了下实现, 在此过程中, 还需要考虑结点不存在的情况。

看下代码:

# 构建二叉堆 
def binaryHeap(arr, lenth, m): 
 temp = arr[m] # 当前结点的值 
 while(2*m+1 < lenth): 
 lchild = 2*m+1 
 if lchild != lenth - 1 and arr[lchild] < arr[lchild + 1]: 
 lchild = lchild + 1 
 if temp < arr[lchild]: 
 arr[m] = arr[lchild] 
 else: 
 break 
 m = lchild 
 arr[m] = temp 
 
 
def heapsort(arr, length): 
 i = int(len(arr)/2) 
 while(i >= 0): 
 binaryHeap(arr, len(arr), i) 
 i = i - 1 
 
 print("二叉堆的物理顺序为:") 
 print(arr) # 输出二叉堆的物理顺序 
 
 
if __name__ == '__main__': 
 arr = [2, 87, 39, 49, 34, 62, 53, 6, 44, 98] 
 
 heapsort(arr, len(arr))

堆排序过程就是依次将最后的结点与首个节点进行对比交换:

# 构建二叉堆
def binaryHeap(arr, lenth, m):
  temp = arr[m] # 当前结点的值
  while(2*m+1 < lenth):
    lchild = 2*m+1
    if lchild != lenth - 1 and arr[lchild] < arr[lchild + 1]:
      lchild = lchild + 1
    if temp < arr[lchild]:
      arr[m] = arr[lchild]
    else:
      break
    m = lchild
  arr[m] = temp


def heapsort(arr, length):
  i = int(len(arr)/2)
  while(i >= 0):
    binaryHeap(arr, len(arr), i)
    i = i - 1

  print("二叉堆的物理顺序为:")
  print(arr) # 输出二叉堆的物理顺序

  i = length-1
  while(i > 0):
    arr[i], arr[0] = arr[0], arr[i] # 变量交换
    binaryHeap(arr, i, 0)
    i = i - 1560


def pop(arr):
  first = arr.pop(0)
  return first


if __name__ == '__main__':
  arr = [2, 87, 39, 49, 34, 62, 53, 6, 44, 98]

  heapsort(arr, len(arr))

  print("堆排序后的物理顺序")
  print(arr) # 输出经过堆排序之后的物理顺序

  data = pop(arr)
  print(data)

  print(arr)

python封装了一个堆模块, 我们使用该模块可以很高效的实现一个优先队列

import heapq


class Item:
  def __init__(self, name):
    self.name = name

  def __repr__(self):
    return 'Item({!r})'.format(self.name)


class PriorityQueue:
  def __init__(self):
    self._queue = []
    self._index = 0

  def push(self, item, priority):
    heapq.heappush(self._queue, (-priority, self._index, item)) # 存入一个三元组
    self._index += 1

  def pop(self):
    return heapq.heappop(self._queue)[-1] # 逆序输出


if __name__ == '__main__':
  p = PriorityQueue()
  p.push(Item('foo'), 1)
  p.push(Item('bar'), 5)
  p.push(Item('spam'), 4)
  p.push(Item('grok'), 1)

  print(p.pop())
  print(p.pop())

具体请看heapq官网

以上这篇python下实现二叉堆以及堆排序的示例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python开发之字符串string操作方法实例详解
Nov 12 Python
python django事务transaction源码分析详解
Mar 17 Python
Python闭包的两个注意事项(推荐)
Mar 20 Python
Python 批量合并多个txt文件的实例讲解
May 08 Python
python 怎样将dataframe中的字符串日期转化为日期的方法
Sep 26 Python
Python:合并两个numpy矩阵的实现
Dec 02 Python
Python如何实现在字符串里嵌入双引号或者单引号
Mar 02 Python
python3 sorted 如何实现自定义排序标准
Mar 12 Python
Python垃圾回收机制三种实现方法
Apr 27 Python
Nginx+Uwsgi+Django 项目部署到服务器的思路详解
May 08 Python
在 Windows 下搭建高效的 django 开发环境的详细教程
Jul 27 Python
Python2及Python3如何实现兼容切换
Sep 01 Python
Python数据结构与算法之链表定义与用法实例详解【单链表、循环链表】
Sep 28 #Python
Python实现压缩和解压缩ZIP文件的方法分析
Sep 28 #Python
Python有序字典简单实现方法示例
Sep 28 #Python
python操作MySQL 模拟简单银行转账操作
Sep 27 #Python
python利用urllib和urllib2访问http的GET/POST详解
Sep 27 #Python
python django使用haystack:全文检索的框架(实例讲解)
Sep 27 #Python
浅谈python和C语言混编的几种方式(推荐)
Sep 27 #Python
You might like
编写自己的php扩展函数
2006/10/09 PHP
PHP生成HTML静态页面实例代码
2008/08/31 PHP
php获取网站百度快照日期的方法
2015/07/29 PHP
Zend Framework教程之Zend_Db_Table表关联实例详解
2016/03/23 PHP
PHP实现下载远程图片保存到本地的方法
2017/06/19 PHP
关于ThinkPhp 框架表单验证及ajax验证问题
2017/07/19 PHP
PHP实现超简单的SSL加密解密、验证及签名的方法示例
2017/08/28 PHP
Nigma vs AM BO3 第二场2.13
2021/03/10 DOTA
收藏Javascript中常用的55个经典技巧
2007/08/12 Javascript
capacityFixed 基于jquery的类似于新浪微博新消息提示的定位框
2011/05/24 Javascript
js 分页全选或反选标识实现代码
2011/08/09 Javascript
常用Extjs工具:Extjs.util.Format使用方法
2012/03/22 Javascript
鼠标悬浮停留三秒后自动显示大图js代码
2014/09/09 Javascript
js+css实现tab菜单切换效果的方法
2015/01/20 Javascript
JavaScript判断表单中多选框checkbox选中个数的方法
2015/08/17 Javascript
jQuery的 $.ajax防止重复提交的两种方法(推荐)
2016/10/14 Javascript
详解Webpack DLL用法以及功能
2017/07/11 Javascript
Vue-router结合transition实现app前进后退动画切换效果的实例
2017/10/11 Javascript
微信小程序的线程架构【推荐】
2019/05/14 Javascript
vue pages 多入口项目 + chainWebpack 全局引用缩写说明
2020/09/21 Javascript
[10:14]2018DOTA2国际邀请赛寻真——paiN Gaming不仅为自己而战
2018/08/14 DOTA
[01:01:18]VP vs NIP 2019国际邀请赛小组赛 BO2 第二场 8.15
2019/08/17 DOTA
Python正则表达式经典入门教程
2017/05/22 Python
Python中协程用法代码详解
2018/02/10 Python
利用python下载scihub成文献为PDF操作
2020/07/09 Python
英国豪华装饰照明品牌的在线零售商:Inspyer Lighting
2019/12/10 全球购物
个人职业生涯规划书1500字
2013/12/31 职场文书
物流仓储计划书
2014/01/10 职场文书
便利店促销方案
2014/02/20 职场文书
无犯罪记录证明
2014/09/19 职场文书
村主任“四风”问题个人对照检查材料思想汇报
2014/10/02 职场文书
优秀教师个人材料
2014/12/15 职场文书
2016年度创先争优活动总结
2016/04/05 职场文书
创业计划书之校园超市
2019/09/12 职场文书
Python实现机器学习算法的分类
2021/06/03 Python
Java实现二分搜索树的示例代码
2022/03/17 Java/Android