コード例 #1
0
ファイル: minheap.c プロジェクト: dr107/CPrimer
/*
  Return the array position of the smaller child of the element
  at the postion i, or i itself if it's the smallest. Return -1
  if i is a leaf. Checks if the children are valid, but not i
  itself.
 */
int smaller_child(heap *h, unsigned i)
{
        unsigned i_lc=childl(i);
        unsigned i_rc=childr(i);
        if (is_valid_ind(h, i_lc) && is_valid_ind(h, i_rc)) {
                return smallest_el(h, i, smallest_el(h, i_lc, i_rc));
        } else if (is_valid_ind(h, i_lc)) {
                return smallest_el(h, i, i_lc);
        } else if (is_valid_ind(h, i_rc)) {
                return smallest_el(h, i, i_rc);
        } else {
                return -1;
        }
}
コード例 #2
0
ファイル: heap.c プロジェクト: bassettmb/heap
/**
 * Bubbles an element of the heap downwards into a position where it satisfies
 * the max-heap property.
 */
void
heap_bubbledown(struct heap *heap, size_t ix)
{
    void *elem, *child;
    size_t lim, last;

    assert(heap);

    if (heap->nelems < 2) return; /* nothing to bubble down */
    if (ix > heap->nelems) return; /* index is out of bounds */

    last = heap->nelems - 1;

    /* the limiting element is the last element with children and the
     * only element that may have fewer than two children
     */

    lim = parent(last);
    elem = offset(heap, ix);


    /* here we handle the traversal through
     * heap elements linked to children
     */
    while (ix < lim) {
        void *other;
        size_t cix;

        /* since we have not yet reached the limit element, we know that each
         * parent we encounter will have two children
         */

        cix = childl(ix);
        child = offset(heap, cix);
        other = succ(heap, child);


        /* we pick the greater child to ensure that this subheap will satisfy
         * the heap property after we rearrange its elements
         */

        if (compare(heap, child, other) < 0) {
            ++cix;
            child = other;
        }

        /* if we satisfy the heap property, we are done */
        if (compare(heap, elem, child) >= 0) return;

        /* otherwise, we reorder the element with its greater child
         * and continue restoring the heap property
         */
        swap(heap, elem, child);
        ix = cix;
        elem = child;
    }

    if (ix > lim) return; /* element has no child and is at its correct index */

    /* if we have not yet returned, we know our current element is the limiting
     * element and that the last element is a child of the limiting element
     */

    child = offset(heap, last);

    /* if nelems is odd, the final subtree has two children */
    if (heap->nelems & 1) {
        void *other;
        other = pred(heap, child);
        if (compare(heap, child, other) < 0)
            child = other;
    }

    /* to fully restore the heap property,
     * we swap this element into place and are done
     */
    if (compare(heap, elem, child) < 0)
        swap(heap, elem, child);
}