/*===========*\ | binheap.h | \*===========*/ #ifndef _BINHEAP_H_ #define _BINHEAP_H_ #define ElementType int #define MinPQSize 2 #define MinData -10000 typedef struct HeapStruct { int Capacity; int Size; ElementType * Elements; } * PriorityQueue; //function list PriorityQueue Initialize(int MaxElements); void Destroy(PriorityQueue h); void MakeEmpty(PriorityQueue h); void Insert(ElementType x,PriorityQueue h); ElementType DeleteMin(PriorityQueue h); ElementType FindMin(PriorityQueue h); int IsEmpty(PriorityQueue h); int IsFull(PriorityQueue h); #endif /*=============*\ | binheap.c | \*=============*/ #include "binheap.h" #include <stdio.h> #include <stdlib.h> //初始化优先队列 PriorityQueue Initialize(int MaxElements) { PriorityQueue h; if (MaxElements < MinPQSize) printf("out of space!!\n"); h = (PriorityQueue)malloc(sizeof(struct HeapStruct)); if (h == NULL) printf("out of space!!\n"); h->Elements = (ElementType *)malloc((MaxElements+1)*sizeof(ElementType)); if (h->Elements == NULL) printf("out of space!!\n"); h->Capacity = MaxElements; h->Size = 0; h->Elements[0] = MinData; return h; } //判断队列是否已满 int IsFull(PriorityQueue h) { return h->Size == h->Capacity-1; } //判断队列是否为空 int IsEmpty(PriorityQueue h) { return h->Size == 0; } //插入节点 void Insert(ElementType x,PriorityQueue h) { int i ; if (IsFull(h)) { printf("Priority queue is full\n"); return; } for(i=++h->Size;h->Elements[i/2]>x;i/=2) h->Elements[i] = h->Elements[i/2]; h->Elements[i]=x; } //从节点p下滤 void percolateDown(int p,PriorityQueue h) { int i = p; if (p>h->Size) { printf("Out of the size !! : p=%d,size=%d\n",p,h->Size); return; } ElementType element = h->Elements[p]; while (i*2<=h->Size) { int minChild = (2*i != h->Size) && (h->Elements[2*i]>h->Elements[2*i+1]) ? 2*i+1 : 2*i; if(element>h->Elements[minChild]) { h->Elements[i] = h->Elements[minChild]; i=minChild; } else break; } h->Elements[i] = element; } //从节点P上滤 void percolateUp(int p,PriorityQueue h) { int i; if (p>h->Size) { printf("Out of the size !!\n"); return; } ElementType element = h->Elements[p]; for(i=p;h->Elements[i/2]>element;i=i/2) h->Elements[i] = h->Elements[i/2]; h->Elements[i]=element; } //删除最小元 ElementType DeleteMin(PriorityQueue h) { int i,Child; ElementType MinElement,LastElement; if(IsEmpty(h)) { printf("Priority queue is empty"); return h->Elements[0]; } MinElement = h->Elements[1]; LastElement = h->Elements[h->Size--]; for(i=1;i*2<=h->Size;i=Child) { /* find smaller child */ Child = i*2; if (Child != h->Size && h->Elements[Child+1] < h->Elements[Child]) Child++; /* percolate one level */ if (LastElement > h->Elements[Child]) h->Elements[i] = h->Elements[Child]; else break; } h->Elements[i]=LastElement; return MinElement; } //降低关键字的值 void DecreaseKey(int P,ElementType value,PriorityQueue h) { h->Elements[P] -= value; percolateUp(P,h); } //增加关键字的值 void IncreaseKey(int P,ElementType value,PriorityQueue h) { h->Elements[P] += value; percolateDown(P,h); } //删除节点 void Delete(int P,PriorityQueue h) { DecreaseKey(P,-10000,h); DeleteMin(h); } //构建堆 void BuildHeap(ElementType * et,int n,PriorityQueue h) { int i; h->Size = n; if (n>h->Capacity) { printf("Out of the capacity!\n"); return; } for(i=0;i<n;i++) { h->Elements[i+1] = et[i]; } for(i=n/2;i>0;i--) percolateDown(i,h); } //打印二叉堆(优先队列) void printBinHeap(PriorityQueue h) { int i; for(i=1;i<=h->Size;i++) printf("%d ",h->Elements[i]); putchar('\n'); } // int main() { ElementType a[]={19,18,7,3,4,9,11,22,12}; PriorityQueue h = Initialize(20); BuildHeap(a,sizeof(a)/sizeof(int),h); printBinHeap(h); DecreaseKey(8,20,h); printBinHeap(h); IncreaseKey(1,20,h); printBinHeap(h); Delete(1,h); printBinHeap(h); Insert(3,h); printBinHeap(h); system("pause"); return 0; }