μΆμ²
ChatGPT
ν(Heap) μλ£κ΅¬μ‘°λ μμ μ΄μ§ νΈλ¦¬(Complete Binary Tree)μ ν ννλ‘, μ°μ μμ ν(Priority Queue)λ₯Ό ꡬννλ λ° μ£Όλ‘ μ¬μ©λλ ν¨μ¨μ μΈ μλ£κ΅¬μ‘°μ΄λ€. νμ μμλ€μ μ°μ μμλ₯Ό κΈ°λ°μΌλ‘ λΉ λ₯΄κ² μ΅λκ°μ΄λ μ΅μκ°μ μ°Ύκ³ , μ½μ λ° μμ μμ μ ν¨μ¨μ μΌλ‘ μνν μ μλλ‘ μ€κ³λμλ€.
1. νμ μ£Όμ νΉμ§
μμ μ΄μ§ νΈλ¦¬
νμ λͺ¨λ λ λ²¨μ΄ μμ ν μ±μμ Έ μμΌλ©°, λ§μ§λ§ λ 벨λ μΌμͺ½λΆν° μ±μμ Έ μλ μ΄μ§ νΈλ¦¬μ΄λ€. μ΄ νΉμ± λλΆμ νμ λ°°μ΄(Array)λ‘ ν¨μ¨μ μΌλ‘ ꡬνλ μ μλ€.
ν μμ± Heap Property
μ΅λ ν Max-Heap
λΆλͺ¨ λ Έλμ κ°μ΄ μμ λ Έλμ κ°λ³΄λ€ ν¬κ±°λ κ°μ ꡬ쑰μ΄λ€. λ°λΌμ λ£¨νΈ λ Έλλ νμμ κ°μ₯ ν° κ°μ κ°μ§λ€.
μ΅μ ν Min-Heap
λΆλͺ¨ λ Έλμ κ°μ΄ μμ λ Έλμ κ°λ³΄λ€ μκ±°λ κ°μ ꡬ쑰μ΄λ€. λ°λΌμ λ£¨νΈ λ Έλλ νμμ κ°μ₯ μμ κ°μ κ°μ§λ€.
ν¨μ¨μ μΈ μ κ·Ό
νμ λ£¨νΈ λ Έλμμ μ΅λκ° λλ μ΅μκ°μ΄ μμΉνκΈ° λλ¬Έμ, μ΅λκ° λλ μ΅μκ°μ O(1) μκ°μ μ κ·Όν μ μλ€.
2. νμ ꡬν λ°©λ²
νμ μΌλ°μ μΌλ‘ λ°°μ΄(Array)μ μ΄μ©ν΄ ꡬνλλ€. λ°°μ΄μ μ¬μ©ν΄ νμ ꡬννλ©΄ νΈλ¦¬μ λΆλͺ¨-μμ κ΄κ³λ₯Ό λ°°μ΄μ μΈλ±μ€λ₯Ό ν΅ν΄ μ½κ² κ΄λ¦¬ν μ μλ€.
1. λ°°μ΄μ μ΄μ©ν ν ꡬν
λ Έλ κ°μ κ΄κ³
- λΆλͺ¨ λ Έλ μΈλ±μ€ : (i - 1) / 2
- μΌμͺ½ μμ λ Έλ μΈλ±μ€ : 2 * i + 1
- μ€λ₯Έμͺ½ μμ λ Έλ μΈλ±μ€ : 2 * i + 2
μμ
// λ°°μ΄μ μ΄μ©ν μ΅λ ν μμ
int[] heap = {50, 30, 20, 15, 10, 8, 16};
2. κ°μ²΄λ₯Ό μ΄μ©ν ν ꡬν
κ°μ²΄λ₯Ό μ¬μ©ν΄ νμ ꡬνν μλ μμΌλ©°, κ° λ Έλλ λ€μκ³Ό κ°μ μμ±μ κ°μ§λ€.
- κ° Value : λ Έλμ λ°μ΄ν°
- μΌμͺ½ μμ Left Child
- μ€λ₯Έμͺ½ μμ Right Child
- λΆλͺ¨ λ Έλ Parent
class HeapNode {
int value;
HeapNode left;
HeapNode right;
HeapNode parent;
HeapNode(int value) {
this.value = value;
}
}
3. νμ μ£Όμ μ°μ°
1. μ½μ Insertion
μλ‘μ΄ μμλ₯Ό νμ μΆκ°νλ€.
- μ λ Έλλ₯Ό νμ λ§μ§λ§ μμΉμ μ½μ νλ€.
- ν μμ±μ μ μ§νκΈ° μν΄ ν μ
(Heap Up) μ°μ°μ μννλ€.
- μΆκ°ν λ Έλμ λΆλͺ¨ λ Έλμ λΉκ΅ν΄ νμ μ μμΉλ₯Ό κ΅ννλ€.
- μ΅λ νμ κ²½μ°, λΆλͺ¨ λ Έλλ³΄λ€ ν¬λ©΄ κ΅ννλ€.
- μ΅μ νμ κ²½μ°, λΆλͺ¨ λ Έλλ³΄λ€ μμΌλ©΄ κ΅ννλ€.
- μ΄ κ³Όμ μ 루νΈκΉμ§ λ°λ³΅νλ€.
- ν μ Heap Up : νμ μλ‘μ΄ μμλ₯Ό μ½μ ν λ ν΄λΉ μμκ° λΆλͺ¨ λ Έλλ³΄λ€ μκ±°λ ν¬λ©΄(μ΅μ ν λλ μ΅λ νμ λ°λΌ) λΆλͺ¨μ μμΉ κ΅ν(swap)μ νλ©΄μ μλ‘ μ΄λνλ κ³Όμ μ΄λ€. μ΄ κ³Όμ μ νΈλ¦¬μ λ£¨νΈ λ Έλμ λλ¬νκ±°λ ν μμ±μ΄ μ μ§λ λκΉμ§ κ³μλλ€.
μκ° λ³΅μ‘λ : O(log n)
ꡬν μμ : μ΅λ ν
public void insert(int value) {
// λ°°μ΄μ λ€μ λΉ κ³΅κ°μ κ° μ½μ
heap[size] = value;
size++;
// ν μ
int current = size - 1;
while (current > 0) {
int parent = (current - 1) / 2;
if (heap[current] > heap[parent]) { // μ΅λ ν κΈ°μ€
// κ΅ν
int temp = heap[current];
heap[current] = heap[parent];
heap[parent] = temp;
current = parent;
} else {
break;
}
}
}
μμ (μ΅λ νμ 25 μ½μ )
μ΄κΈ° ν:
20
/ \
15 18
/ \ /
10 12 17
1. 25λ₯Ό λ§μ§λ§ μμΉμ μΆκ°:
20
/ \
15 18
/ \ / \
10 12 17 25
2. λΆλͺ¨μ λΉκ΅νμ¬ μν₯ μ΄λ:
- 25 > 18μ΄λ―λ‘ κ΅ν
20
/ \
15 25
/ \ / \
10 12 17 18
- 25 > 20μ΄λ―λ‘ κ΅ν
25
/ \
15 20
/ \ / \
10 12 17 18
- μ΅μ’
μ΅λ ν μλ£
2. μμ Deletion
μ΅λ νμμλ κ°μ₯ ν° κ°μ, μ΅μ νμμλ κ°μ₯ μμ κ°μ μ κ±°νλ μ°μ°
- λ£¨νΈ λ Έλ(κ°μ₯ ν° κ° λλ κ°μ₯ μμ κ°)λ₯Ό μ κ±°νλ€.
- νμ λ§μ§λ§ λ Έλλ₯Ό 루νΈλ‘ μ΄λμν¨λ€.
- ν λ€μ΄(Heap Down) μ°μ°μ ν΅ν΄ ν μμ±μ μ μ§νλ€.
- λΆλͺ¨ λ Έλλ₯Ό μμ λ Έλμ λΉκ΅ν΄ νμ μ μμΉλ₯Ό κ΅ννλ€.
- μ΅λ νμ κ²½μ°, μμ λ Έλ μ€ λ ν° κ°κ³Ό κ΅ννλ€.
- μ΅μ νμ κ²½μ°, μμ λ Έλ μ€ λ μμ κ°κ³Ό κ΅ννλ€.
- ν λ€μ΄ Heap Down : νμμ λ£¨νΈ λ Έλμ κ°μ μμ ν ν, νμ μμ±(μ΅λ ν λλ μ΅μ ν μμ±)μ μ μ§νκΈ° μν΄ μμ λ Έλμ λΉκ΅νλ©΄μ μλλ‘ μ΄λμν€λ κ³Όμ
μκ° λ³΅μ‘λ : O(log n)
ꡬν μμ : μ΅λ ν
public int remove() {
if (size == 0) throw new NoSuchElementException("Heap is empty");
int root = heap[0];
heap[0] = heap[size - 1];
size--;
// ν λ€μ΄
int current = 0;
while (current < size) {
int left = 2 * current + 1;
int right = 2 * current + 2;
int largest = current;
if (left < size && heap[left] > heap[largest]) {
largest = left;
}
if (right < size && heap[right] > heap[largest]) {
largest = right;
}
if (largest != current) {
// κ΅ν
int temp = heap[current];
heap[current] = heap[largest];
heap[largest] = temp;
current = largest;
} else {
break;
}
}
return root;
}
μμ (μ΅μ νμμ μμ )
μ΄κΈ° ν :
2
/ \
3 4
/ \
7 6
1. λ£¨νΈ λ
Έλ μ κ±°
(2 μμ )
2. λ§μ§λ§ μμλ₯Ό 루νΈλ‘ μ΄λ
6
/ \
3 4
/
7
3. μμκ³Ό λΉκ΅ν΄ νν₯ μ΄λ
- 6 < 3μ΄λ―λ‘ κ΅ν
3
/ \
6 4
/
7
-μ΅μ ν μ΅μ’
μλ£
3. μ°ΎκΈ° Search
- μ΅λ νμμ μ΅λκ° μ°ΎκΈ° : O(1)
- μ΅μ νμμ μ΅μκ° μ°ΎκΈ° : O(1)
- μΌλ°μ μΈ κ° μ°ΎκΈ° : O(n)
- ν μ 체λ₯Ό μμ°¨μ μΌλ‘ νμν΄μΌ νλ€. λλΉ μ°μ νμ(BFS), κΉμ΄ μ°μ νμ(DFS) λ°©μμ μ¬μ©νλ€.
4. νμ ꡬν μμ
μλ°μμ λ°°μ΄μ μ΄μ©ν νμ ꡬν
import java.util.Arrays;
public class MinHeap {
private int[] heap;
private int size;
private int capacity;
public MinHeap(int capacity) {
this.capacity = capacity;
this.size = 0;
this.heap = new int[capacity];
}
// λΆλͺ¨ λ
Έλ μΈλ±μ€
private int getParentIndex(int index) { return (index - 1) / 2; }
// μΌμͺ½ μμ λ
Έλ μΈλ±μ€
private int getLeftChildIndex(int index) { return 2 * index + 1; }
// μ€λ₯Έμͺ½ μμ λ
Έλ μΈλ±μ€
private int getRightChildIndex(int index) { return 2 * index + 2; }
// μ½μ
μ°μ°
public void insert(int value) {
if (size == capacity) throw new IllegalStateException("Heap is full");
heap[size] = value;
size++;
heapifyUp(size - 1); // ν μμ± μ μ§ (μν₯μ μ λ ¬)
}
// ν μ λ ¬ (μν₯μ)
private void heapifyUp(int index) {
while (index > 0 && heap[index] < heap[getParentIndex(index)]) {
swap(index, getParentIndex(index));
index = getParentIndex(index);
}
}
// μ΅μκ°(루νΈ) μμ
public int removeMin() {
if (size == 0) throw new IllegalStateException("Heap is empty");
int min = heap[0];
heap[0] = heap[size - 1];
size--;
heapifyDown(0); // ν μμ± μ μ§ (νν₯μ μ λ ¬)
return min;
}
// ν μ λ ¬ (νν₯μ)
private void heapifyDown(int index) {
int smallest = index;
int left = getLeftChildIndex(index);
int right = getRightChildIndex(index);
if (left < size && heap[left] < heap[smallest]) {
smallest = left;
}
if (right < size && heap[right] < heap[smallest]) {
smallest = right;
}
if (smallest != index) {
swap(index, smallest);
heapifyDown(smallest);
}
}
// λ μμ κ΅ν
private void swap(int i, int j) {
int temp = heap[i];
heap[i] = heap[j];
heap[j] = temp;
}
// ν λ΄μ© μΆλ ₯
public void printHeap() {
System.out.println(Arrays.toString(Arrays.copyOfRange(heap, 0, size)));
}
public static void main(String[] args) {
MinHeap minHeap = new MinHeap(10);
minHeap.insert(20);
minHeap.insert(15);
minHeap.insert(30);
minHeap.insert(5);
minHeap.insert(10);
minHeap.printHeap(); // [5, 10, 30, 20, 15]
System.out.println("Min value removed: " + minHeap.removeMin()); // 5
minHeap.printHeap(); // [10, 15, 30, 20]
}
}
5. νμ μμ©
νμ μ¬λ¬ μκ³ λ¦¬μ¦μμ μ€μν μν μ νλ©°, λ€μν μμ© μ¬λ‘κ° μλ€.
1. μ°μ μμ ν Priority Queue
ν μλ£κ΅¬μ‘°λ μ°μ μμ ν(Priority Queue)λ₯Ό ꡬννλ λ° λ§μ΄ μ¬μ©λλ€. μ μ μμ νμμλ μμκ° λ€μ΄μ¨ μμκ° μλλΌ μ°μ μμμ λ°λΌ μ²λ¦¬λλ©°, νμ μ΅λκ° λλ μ΅μκ°μ ν¨μ¨μ μΌλ‘ κ΄λ¦¬νλ λ° μ 리νλ€.
μλ°μμλ PriorityQueue ν΄λμ€λ₯Ό ν΅ν΄ μ΅μ ν κΈ°λ°μ μ°μ μμ νλ₯Ό μ 곡νλ€. κΈ°λ³Έμ μΌλ‘ μ€λ¦μ°¨μμΌλ‘ λμνλ©°, μ¬μ©μκ° μ μν μ°μ μμλ‘ μ λ ¬ν μ μλ€.
2. ν μ λ ¬ Heap Sort
ν μ λ ¬(Heap Sort)μ ν μλ£κ΅¬μ‘°λ₯Ό μ΄μ©ν μ λ ¬ μκ³ λ¦¬μ¦μΌλ‘, μ΅λ νμ΄λ μ΅μ νμ ꡬμ±ν ν, λ£¨νΈ λ Έλλ₯Ό μ κ±°νκ³ μ¬μ λ ¬νλ κ³Όμ μ λ°λ³΅ν΄ μ λ ¬μ μννλ€.
- ν μ λ ¬μ μκ° λ³΅μ‘λλ O(log n)μΌλ‘, λΉκ΅ κΈ°λ° μ λ ¬ μκ³ λ¦¬μ¦ μ€ ν¨μ¨μ μΈ νΈμ΄λ€.
- μ μ리 μ λ ¬(in-place sorting)μ΄ κ°λ₯νμ§λ§, μμ μ μΈ μ λ ¬(stable sorting)μ μλλ€.
- κ΄λ ¨ κΈ -> [μκ³ λ¦¬μ¦] μ μ리 μ λ ¬ In-Place Sorting
- κ΄λ ¨ κΈ -> [μκ³ λ¦¬μ¦] μμ μ μΈ μ λ ¬ Stable Sorting
3. λ€μ΅μ€νΈλΌ μκ³ λ¦¬μ¦ Dijkstra's Algorithm
λ€μ΅μ€νΈλΌ μκ³ λ¦¬μ¦μ μ΅λ¨ κ²½λ‘ μκ³ λ¦¬μ¦ μ€ νλλ‘, μ°μ μμ νλ₯Ό μ¬μ©ν΄ κ°μ€μΉκ° μλ κ·Έλνμμ μ΅λ¨ κ²½λ‘λ₯Ό μ°Ύλλ€. μ΄ κ³Όμ μμ μ΅μ νμ΄ μ¬μ©λμ΄, νμ¬κΉμ§ κ°μ₯ μμ 거리λ₯Ό κ°μ§ μ μ μ ν¨μ¨μ μΌλ‘ μ νν μ μλ€.
4. μ΄μ§ ν(Binary Heap)κ³Ό νμ΄λ§ ν(Pairing Heap)
νμ μ¬λ¬ λ³ν μ€ νλμΈ μ΄μ§ νκ³Ό νμ΄λ§ νμ κ°κΈ° λ€λ₯Έ νΉμ§κ³Ό μ₯μ μ κ°μ§κ³ μμΌλ©°, μ΄μ§ νμ κ°μ₯ κΈ°λ³Έμ μΈ ννμ΄κ³ , νμ΄λ§ νμ λ 볡μ‘νμ§λ§ μ½μ κ³Ό μμ κ° λμ± ν¨μ¨μ μ΄λ€.
'λΉ κ΅¬λ© μ±μ°κΈ°' μΉ΄ν κ³ λ¦¬μ λ€λ₯Έ κΈ
[Java] PriorityQueue (2) | 2024.09.18 |
---|---|
[μλ£ κ΅¬μ‘°]μ΄μ§ ν Binary Heap (1) | 2024.09.18 |
[μκ³ λ¦¬μ¦] μμ μ μΈ μ λ ¬ Stable Sorting (1) | 2024.09.15 |
[μκ³ λ¦¬μ¦] μ μ리 μ λ ¬ In-Place Sorting (1) | 2024.09.15 |
[Java] Queue μΈν°νμ΄μ€ (1) | 2024.09.14 |