python實現堆排序代碼

        堆排序的最好,最壞的時間複雜度都爲nlogn。當我們需要對一個沒有順序的序列進行堆排序,首先需要將這批數據轉化成堆。一般來說,對序列進行降序排列一般使用大頂堆。大頂堆必須滿足:data[index] >= data[2*index + 1] 並且滿足data[index] >= data[2*index + 2]。前提是父節點有相應的子節點。按照定義,我們需要找到所有的非葉子節點,因爲按照堆的定義,我們只需要交換父節點和某個子節點的值,當它們之間的關係不滿足堆。

        對於大頂堆。爲什麼要從下往上,從左往右呢?至於爲什麼要從左往右,想必大家都知道,這是沿着序列索引遞減的方向,我很容易的就能控制當前的索引,說白了就是爲了方便;從下往上,主要是按照順組建立大頂堆,這是個遞歸的過程。最後整棵樹中的每一個堆都是大頂堆。下面給出python編制的代碼:

import sys
import math  # 向上取整


class Solution:
    def __init__(self):
        pass

    def re_shape(self, data, final_index):
        tmp = final_index
        while True:
            cur_change = False
            if final_index == 0:
                parent_index = 0
            else:
                parent_index = math.ceil(final_index / 2.0) - 1  # 第一個父節點
            left_child = 2 * parent_index + 1
            right_child = left_child + 1
            # print([parent_index, left_child, right_child])
            if left_child <= final_index:
                if right_child <= final_index:
                    max_param = max([data[left_child], data[right_child]])
                    index = data.index(max_param)
                    if max_param > data[parent_index]:
                        data[parent_index], data[index] = data[index], data[parent_index]
                        cur_change = True
                elif data[left_child] > data[parent_index]:
                        data[parent_index], data[left_child] = data[left_child], data[parent_index]
                        cur_change = True
                final_index = left_child - 1  # 新的起點
                if cur_change and final_index <= 0:
                    final_index = tmp
                if not final_index:
                    return data
            else:
                return data

    def get_data(self):
        str_dig = sys.stdin.readline().split()
        try:
            data = list(map(lambda x: int(x), str_dig))
            final_index = len(data) - 1
            for cur_index in range(0, len(data), 1):
                data = self.re_shape(data, final_index)
                data[0], data[final_index] = data[final_index], data[0]
                final_index -= 1
            return data
        except:
            assert 'Error'

if __name__ == '__main__':
    so = Solution()
    sys.stdout.write(str(so.get_data()))
30 40 67 74 65 75 120 4 6 90
[4, 6, 30, 40, 65, 67, 74, 75, 90, 120]
Process finished with exit code 0


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章