堆邏輯上是一棵完全二叉樹
堆物理上是儲存在陣列中
滿足任意結點的值都大於其子樹中結點的值,叫做大堆,或者大根堆,或者最大堆
反之,則是小堆,或者小根堆,或者最小堆
(1)向下調整
過程(以小堆為例):
index 如果已經是葉子結點,則整個調整過程結束
判斷 index 位置有沒有孩子
因為堆是完全二叉樹,沒有左孩子就一定沒有右孩子,所以判斷是否有左孩子
因為堆的儲存結構是陣列,所以判斷是否有左孩子即判斷左孩子下標是否越界,即 left >= size 越界
確定 left 或 right,誰是 index 的最小孩子 min
如果右孩子不存在,則 min = left
否則,比較 array[left] 和 array[right] 值得大小,選擇小的為 min
比較 array[index] 的值 和 array[min] 的值,如果 array[index] <= array[min],則滿足堆的性質,調整結束
否則,交換 array[index] 和 array[min] 的值
然後因為 min 位置的堆的性質可能被破壞,所以把 min 視作 index,向下重複以上過程
**實現:
public
static
void
adjustdown
(int
array,
int size,
int index)
// 2. 找最小的孩子
int minindex = leftindex;
int rightindex = leftindex +1;
if(rightindex < size && array[rightindex]
< array[leftindex]
)// 3. 比較最小孩子的值 和 index 位置的值
if(array[index]
<= array[minindex]
)// 4. 交換
int t = array[index]
; array[index]
= array[minindex]
; array[minindex]
= t;
// 5. 把最小的孩子視為 index,繼續迴圈
index = minindex;
}}
(2)建堆
過程:我們給出乙個陣列,這個陣列邏輯上可以看做一顆完全二叉樹,但是還不是乙個堆,現在我們通過演算法,把它構建成乙個堆。根節點左右子樹不是堆,我們怎麼調整呢?這裡我們從倒數的第乙個非葉子節點的子樹開始調整,一直調整到根節點的樹,就可以調整成堆。
**實現:
public
static
void
createheap
(int
array,
int size)
}
優先順序佇列
概念:在很多應用中,我們通常需要按照優先順序情況對待處理物件進行處理,比如首先處理優先順序最高的物件,然後處理次高的物件。最簡單的乙個例子就是,在手機上玩遊戲的時候,如果有來電,那麼系統應該優先處理打進來的**。在這種情況下,我們的資料結構應該提供兩個最基本的操作,乙個是返回最高優先順序物件,乙個是新增新的物件。這種資料結構就是優先順序佇列(priority queue)
操作:一、 入佇列:
首先按尾插方式放入陣列
比較其和其雙親的值的大小,如果雙親的值大,則滿足堆的性質,插入結束
否則,交換其和雙親位置的值,重新進行 2、3 步驟
直到根結點
二、出佇列:
為了防止破壞堆的結構,刪除時並不是直接將堆頂元素刪除,而是用陣列的最後乙個元素替換堆頂元素,然後通過向下調整方式重新調整成堆
三、返回隊首元素
**實現如下:
public
class
mypriorityqueue
public integer element()
return array[0]
;}// o(log(n))
public integer remove()
int e = array[0]
; array[0]
= array[size -1]
; size--
;adjustdown(0
);return e;
}// o(log(n))
public
void
add(integer e)
private
void
adjustup
(int index)
// 2. 找到 index 的父節點
int parentindex =
(index -1)
/2;// 3. 比較 父節點的值 和 index 的值
// 4. 只要父節點的值 <= index 的值,調整結束
if(array[parentindex]
<= array[index]
)// 5. 交換 父節點 和 index 位置的值
int t = array[index]
; array[index]
= array[parentindex]
; array[parentindex]
= t;
// 6. 把 父節點看作 index,繼續這個大迴圈
index = parentindex;}}
private
void
adjustdown
(int index)
int rightindex = leftindex +1;
int minindex = leftindex;
if(rightindex < size && array[rightindex]
< array[leftindex])if
(array[index]
<= array[minindex]
)int t = array[index]
; array[index]
= array[minindex]
; array[minindex]
= t;
index = minindex;}}
}
堆(Heap)的實現
這次實現了堆,這個堆不是指系統堆疊的堆,是一種資料結構,見下圖 堆的本質就是乙個陣列 上圖中,紅色的是值,黑色的是下標 簡單的來說就是把乙個陣列看成是二叉樹,就像上圖 大堆和小堆分別是指根節點比孩子節點的值大或者是小,看了上圖之後就可以發現,父親節點和孩子節點之間下表的關係,parnet child...
堆 Heap 的實現
什麼是堆?優先佇列 opriority queue 特殊的 佇列 取出元素的順序是依照元素的優先權 關鍵字 大小,而不是元素進入佇列的先後順序。堆有兩大特性 1,結構性 是一顆完全二叉樹。2,有序性 每個葉子結點到根結點都是有序的,如果是公升序,那麼就是最大堆,否則為最小堆。這些是堆 下面的不是堆 ...
堆(Heap)的實現
這次實現了堆,這個堆不是指系統堆疊的堆,是一種資料結構,見下圖 堆的本質就是乙個陣列 上圖中,紅色的是值,黑色的是下標 簡單的來說就是把乙個陣列看成是二叉樹,就像上圖 大堆和小堆分別是指根節點比孩子節點的值大或者是小,看了上圖之後就可以發現,父親節點和孩子節點之間下表的關係,parnet child...