zoukankan      html  css  js  c++  java
  • 排序算法:堆排序

    堆排序的时间复杂度为O(nlgn),由于堆是一个完全二叉树的形式,因此可以用数组来存储,通过下标的关系表示二叉树结点的父子、兄弟关系。

    堆分为大顶堆以及小顶堆,以大顶堆为例。大顶堆的性质是每一个父节点的值都比孩子结点的值大,这是需要维护的最重要的性质。

    在进行堆排序时,首先是将一个无序数组建成一个堆的形式,再将最后一个叶子结点和堆顶元素交换,得到最大值,然后从根结点开始向下维护堆性质,如此循环。

    python实现:

     1 #堆排序算法
     2 def left(i) : #左孩子下标
     3     return(2 * i + 1)
     4 
     5 
     6 def right(i): #右孩子下标
     7     return(2 * i)
     8 
     9 
    10 def MAX_HEAPIFY(A, i, end):  #维护堆的性质
    11     l = left(i)
    12     r = right(i)
    13     heap_size = len(A)
    14     if l < end and A[l] > A[i]: #保证当前父结点存在左孩子,找到三个结点中的最大值的下标
    15         largest = l
    16     else:
    17         largest = i
    18     if r < end and A[r] > A[largest]:
    19         largest = r
    20     if largest != i: #如果最大值的下标不是根节点,则交换两个值
    21         A[largest], A[i] = A[i], A[largest]
    22         MAX_HEAPIFY(A, largest, end) #以交换过的孩子结点的下标作为下一次的父结点,进行递归
    23 
    24 
    25 def Build_max_heap(A): #将无序数组构建成为大顶堆
    26     heap_size = len(A)
    27     for i in range(heap_size//2, -1, -1): #从最后一个非叶子结点开始维护,逐个向上直到根节点
    28         MAX_HEAPIFY(A, i, heap_size)
    29 
    30 
    31 def Max_heap_sort(A): #堆排序算法
    32     Build_max_heap(A) #先获得大顶堆
    33     for i in range(len(A)-1, 0, -1):
    34         A[i], A[0] = A[0], A[i] #将末尾结点和跟根节点交换
    35         MAX_HEAPIFY(A, 0, i) #每交换一次,获得一个最大值,然后从根节点开始维护堆的性质
    36                              #并去掉最后一个位置元素
    37 
    38 if __name__=='__main__':
    39     list = [10, 6, 5, 8, 1, 2, 4, 9]
    40     Max_heap_sort(list)
    41     print(list)

    结果为[1, 2, 4, 5, 6, 8, 9, 10]

    这里要注意的是在MAX_HEAPIFY函数中加入结束时的下标,以此去掉数组结尾已经获得的排好序的部分。

  • 相关阅读:
    MarkDown的快速入门
    openCV打开摄像头,用openGL实现纹理贴图和视频预览
    tensorflow中的dropout是怎么实现的?
    BEEPS-仿美图秀秀磨皮算法,让美女的皮肤更光滑
    鄙人提出的PBDRLSE分割算法(绝对原创)
    怀旧风格照片特效
    铅笔特效算法
    背光图像的增强
    关于push和concat的性能问题
    小程序日历签到
  • 原文地址:https://www.cnblogs.com/XinL-blog/p/11650960.html
Copyright © 2011-2022 走看看