堆排序也是一種時間複雜度為o(n
lgn)
\omicron (n\lg n)
o(nlgn)
的排序演算法,但是與歸併排序不同的是堆排序是一種原址排序,也就是說排序過程只是交換資料的位置。
堆是乙個陣列,儲存乙個近似完全二叉樹,樹上的每個結點對應陣列中的乙個元素,陣列第乙個元素儲存根節點,第i個元素的左孩子在陣列的2i位置,右孩子在陣列的2i+1位置,父結點在陣列的i/2位置。
最大堆指一種父節點必然大於等於子節點的堆。下圖為乙個最大堆的儲存情況:
max-heapify是維護最大堆性質的重要方法。max-heapify的輸入為陣列a和下標i,當呼叫max-heapify時,假定根節點為left(i)和right(i)的二叉樹都是最大堆,但是a[i]可能比它的子節點要小。max-heapify通過讓a[i]的值在最大堆中逐級下降,從而使得以下標i為根節點的樹符合最大堆的性質。以下是max-heapify的偽**以及max-heapify(a, 2)的處理過程:
因為堆的高度為lgn
\lg n
lgn,所以該過程的時間複雜度是o(lg
n)\omicron (\lg n)
o(lgn).
自下而上的呼叫max-heapify可以把乙個陣列轉換為最大堆。
葉子節點不需要呼叫,所以從下標為n/2的的元素開始,一直到根節點。
偽**和建堆過程如下:
利用build-max-heap方法構建最大堆
接著迴圈的堆的根節點和最後乙個元素交換
堆的大小減一
呼叫max-heapify(a, 1)
迴圈2-4步,直到堆中只剩根節點
偽**,以及2-5步過程如下:
堆除了堆排序還有很多應用,比如優先佇列。優先佇列也有兩種最大優先佇列和最小優先佇列。
乙個最大優先佇列支援以下操作:
insert(s, x)
maximum(s)
extract-max(s)
increase-key(s, x, k)
最大優先佇列的應用有很多,其中乙個是在共享計算機系統的作業排程。最大優先佇列記錄將要執行的各個作業及他們之間的相對優先順序。
最小優先佇列可以被用於基於事件驅動的模擬器。佇列中儲存要模擬的事件,每個事件都有乙個發生時間作為其關鍵字。
思考題
github source: 堆排序.md
演算法導論 6 堆排序
堆的分類 最大堆性質 高度 對於堆的一些基本操作 偽 描述 實現 max heapify python實現 123 4567 891011 1213 def max heapify i print max heapify i l left i r right i if l heap size and...
演算法導論 python實踐(6 堆排序)
簡單來講就是將陣列按照完全二叉樹的形式排列。葉節點的元素個數最多為2 n 1 次方,其中n為堆高度。最大堆 某一根葉節點的元素小於等於根節點的數值。通常用於排序 最小堆 某一根葉節點的元素大於等於根節點的數值。通常用於構造優先佇列 首先建立最大堆 函式輸入引數為乙個序列和序列的某一下標。對於某一下標...
演算法導論讀書筆記(6)堆排序
複雜度o nlgn 原址排序 集插入排序和歸併排序兩者的優點 計算給定節點下標i的父,左孩子,右孩子的下標 parent i return i 2 left i return 2i right i return 2i 1 最大堆 堆中最大元素存放在根結點 最小堆 堆中最小元素存放在根結點 從a i ...