python实现大顶堆调整 堆排序

origin = [31, 72, 83, 42, 59, 13, 61, 25, 92]
origin = [0] + origin  # 后面用索引 方便对应规则
count_point = len(origin) - 1
def print_tree(array,unit_width=2): #打印出二叉树的样子,方便观察
    '''
    depth = 4 (深度) 每层满个数(2的(层数-1)次方)  打印出儿叉树的样子 每层前后补空格 空格规律前空格 7310 间隔空格0731
    1 3  7     0
    2 2  3     7
    3 1  1     3
    4 0  0     1
    :param array:
    :param unit_width:
    :return:
    '''
    length = len(array)
    depth = len(bin(length))-2
    index = 1
    space = ' '*unit_width
    for i in range(depth-1,-1,-1):
        pre = 2 ** i - 1#前空格数目
        print(pre * space,end='')
        offset = 2 ** (depth -i -1)#每层起点索引
        line = array[index:index+offset] #每层开始至结束
        lafter = space*(2*pre+1)#后空格数目
        print(lafter.join(map(str,line)))
        #print(line)
        index += offset
print_tree(origin)
print(count_point)
def heap_adjust(array,i,count_point): #堆调整左右先假设一个是两个之中最大的(目的不交换两个的位置取出索引) 然后比较一下 得到最大的数的索引
    while 2 * i <= count_point:
        lchild_index = 2 * i
        max_child_index = lchild_index
        if count_point > lchild_index and array[lchild_index] < array[lchild_index+1]:
            max_child_index = lchild_index + 1
        if array[max_child_index] > array[i]: #如果此父节点比他儿子节点的一个值要小  两节点交换位置
            array[i], array[max_child_index] = array[max_child_index], array[i]
            i = max_child_index #值换了 对应索引再换回来 相当于为上一层准备了 下面的假设最大数的索引
        else:
            break
def max_heap(array:list):
    for i in range(count_point//2,0,-1):# 找到最后一个有叶子节点的堆
        heap_adjust(array,i,count_point)#其实就是 heap_adjust的反复循环 直到每个父节点 都比子节点数值大
    return  array
# print_tree(max_heap(origin)) #调整并不能排序 无叶子节点的 兄弟节点之间的顺序
# print(origin)
def sort(array:list,count_point):
    while count_point > 1: #当节点数 大于一 对照count_point -=1 来看 循环的过程中节点数在减小 为什么 往下看
        array[1], array[count_point] = array[count_point], array[1] #不断将最后一个节点放到(根节点的位置上),由于根结点经过大顶堆 调整后每次都会是最大的那个这样每次取出就是排序
        count_point -= 1 #任何排序都有有序区和无序区  无序区的减有序区的增  节点数减一即根节点放入了列表尾部索引对应即有序区慢慢增大
        if count_point == 2 and array[2] >= array[1]:# 最后两个数不需要再进入堆调整  直接比较一下 排个序
            break
        heap_adjust(array,1,count_point)
    return array
max_heap(origin)#1.调出大顶堆
print_tree(origin)
sort(origin,count_point)#2.排序
print_tree(origin)
print(origin)#3.结果

border="0" width="330" height="86" src="//music.163.com/outchain/player?type=2&id=482894&auto=1&height=66">


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值