/* --- Function: int HEAPinsert(Heap hp, const void *data) --- */ int HEAPinsert(Heap hp, const void *data) { void *tmp; int currpos, parentpos; /* Allocate storage for the new node */ if ((tmp = realloc(hp->tree, (HEAPsize(hp) + 1) * sizeof(void *))) == NULL) return -1; else hp->tree = (void **)tmp; /* Insert the node after the last node */ hp->tree[HEAPsize(hp)] = (void *)data; /* Heapify the tree by pushing the contents of the new node upward */ currpos = HEAPsize(hp); parentpos = HEAPparent(currpos); while (currpos > 0 && hp->compare(hp->tree[parentpos], hp->tree[currpos]) < 0) { /* Swap the contents of the current node and its parent */ tmp = hp->tree[parentpos]; hp->tree[parentpos] = hp->tree[currpos]; hp->tree[currpos] = tmp; /* Move up one level in the tree to continue heapifying */ currpos = parentpos; parentpos = HEAPparent(currpos); } /* Adjust the size of the heap to account for the inserted node */ hp->size++; return 0; }
/* --- Function: void HEAPdestroy(Heap hp) --- */ void HEAPdestroy(Heap hp) { int i; if (hp->destroy != NULL) { for (i = 0; i < HEAPsize(hp); i++) hp->destroy(hp->tree[i]); } free(hp->tree); free(hp); }
/* --- Function: int PQUEUEsize(PQueue pq) --- */ int PQUEUEsize(PQueue pq) { return HEAPsize(pq); }
/* --- Function: int HEAPextract(Heap hp, void **data) --- */ int HEAPextract(Heap hp, void **data) { void *save, *temp; int currpos, leftpos, rightpos, tmppos; /* Do not allow extraction from an empty heap */ if (HEAPsize(hp) == 0) return -1; /* Extract and return node data at the top of the heap */ *data = hp->tree[0]; /* Store/Backup data of the last noded of the heap */ save = hp->tree[HEAPsize(hp) - 1]; /* Adjust(=Shrink) the size of the heap */ if (HEAPsize(hp) - 1 > 0) { if ((temp = (void **)realloc(hp->tree, (HEAPsize(hp) - 1) * sizeof(void *))) == NULL) return -1; else hp->tree = temp; /* Adjust the size of the heap to account for the extracted node */ hp->size--; } else { /* Manage the heap when extracting the last node - and return from call */ free(hp->tree); hp->tree = NULL; hp->size = 0; return 0; } /* Copy the (earlier saved), last node - to the top */ hp->tree[0] = save; /* Heapify the tree by pushing the contents of the new top - downwards... */ currpos = 0; /* leftpos = HEAPleft(currpos); */ /* rightpos = HEAPright(currpos); */ while (1) { /* Select the child to swap with the current node */ leftpos = HEAPleft(currpos); rightpos = HEAPright(currpos); if (leftpos < HEAPsize(hp) && hp->compare(hp->tree[leftpos], hp->tree[currpos]) > 0) tmppos = leftpos; else tmppos = currpos; if (rightpos < HEAPsize(hp) && hp->compare(hp->tree[rightpos], hp->tree[tmppos]) > 0) tmppos = rightpos; /* When tmppos is equal to currpos, the heap property has been restored */ if (tmppos == currpos) { /* Time to return to caller... */ break; } else { /* Swap the contents of the current node and the selected child */ temp = hp->tree[tmppos]; hp->tree[tmppos] = hp->tree[currpos]; hp->tree[currpos] = temp; /* Move down one level in the tree to continue heapifying */ currpos = tmppos; } } return 0; }