- 우선 순위의 개념을 큐에 도입한 자료구조
- 각 데이터들은 우선순위를 가지고 있다.
- 우선 순위가 높은 데이터가 먼저 나가게 된다.
- 가장 우선 순위가 낮은 요소를 먼저 삭제
- 가장 우선 순위가 높은 요소를 먼저 삭제
- 완전 이진 트리의 일종으로 우선순위 큐를 위하여 만들어진 자료구조
- 가장 큰 값이나 가장 작은 값을 빠르게 찾아내도록 만들어진 자료구조
- 완전 이진 트리 형태로 구성
- Key(부모노드) >= Key(자식노드)
- 부모노드의 키값은 자식노드의 키값보다 크거나 같다.- 중복된 값을 허용
- key(부모노드) >= key(자식노드)
- key(부모노드) <= key(자식노드)
- 히프는 완전 이진 트리 구성으로 배열 형태로 구현됨
- 루트 노드부터 인덱스 1로 시작
- 왼쪽 자식 인덱스를 알기 위해서는 부모의 인덱스 X 2
- 오른쪽 자식 인덱스를 알기 위해서는 (부모의 인덱스 X 2) + 1
- 부모의 인덱스를 알기 위해서는 자식의 인덱스 / 2
- 새로운 노드를 히프의 마지막 노드로 삽입
- 새로운 노드를 부모 노드들과 교환
typedef struct{
int key;
}element; // 히프의 각 요소
typedef struct{
element heap[100]; // 히프를 구현할 1차원 배열
int heap_size; // 현재 히프안에 저장된 요소의 갯수
}HeapType;
void insert_max_heap(HeapType* h, element item) // 삽입 연산 함수
{
int i;
i = ++(h->heap_size); // i를 증가시켜 히프의 마지막 노드에 삽입
while((i != 1) && (item.key > h->heap[i / 2].key)){ // i가 루트노드가 아니고, 삽입할 원소가 부모노드이 키 값보다 큰 경우
h->heap[i] = h->heap[i / 2]; // 현재 위치 i를 부모노드의 값으로 변경
i /= 2; // 부모노드 인덱스로 이동
}
h->heap[i] = item; // 최종 위치 i에 원소 삽입
}
- 제일 최대값(최소값)인 루트노드를 제거
- 히프트리 재구성
element delete_max_heap(HeapType* h) // 삭제연산 함수
{
int parent, child; // 부모노드와 자식노드의 인덱스
element item, temp;
item = h->heap[1]; // 삭제할 루트노드의 값 저장
temp = h->heap[(h->heap_size)--]; // 히프의 마지막값 저장 후 사이즈 감소
parent = 1;
child = 2;
while(child <= h->heap_size){ // 자식노드가 존재할 때까지 반복
if ((child < h->heap_size) && (h->heap[child].key) < h->heap[child + 1].key) // 현재 자식노드의 인덱스가 히프의 크기를 벗어나지 않고 오른쪽 자식노드의 키값이 더 큰 경우
child++; // child를 증가시켜 오른쪽 자식노드의 인덱스로 이동
if(temp.key >= h->heap[child].key) // 마지막 노드의 키 값이 현재 자식노드의 키 값보다 큰 경우 종료
break;
h->heap[parent] = h->heap[child]; // 자식노드를 부모노드의 위치로 이동
parent = child; // parent와 child 인덱스를 이동시켜 다음 자식과 비교
child *= 2;
}
h->heap[parent] = temp; // 최종적으로 마지막 노드가 저장될 위치
return item; // 삭제할 원소 반환
}
유익한 글이었습니다.