Lecture 13 - Problems

Here is the same barebones Heap class we’ve seen already, with method specs and headers but no implementation.

public class Heap {
  int[] A;
  int size;
  
  /** Add the value v to the heap. */
  public void add(int v);
  
  /** Return the smallest value in the heap without modifying the heap.
    * Precondition: size >= 1 */
  public int peek();
  
  /** Remove and return the minimum value in the heap.
    * Precondition: size >= 1 */
  public int poll();

}
  1. The kind of heap we’ve been talking about are formally called “min-heaps”, because the minimum value is always at the root. It is also possible to create a “max-heap”, where the maximum value is at the root. How do we need to change the definition (properties) of a heap to switch it from a min-heap to a max-heap?

  2. There is a sorting algorithm called HeapSort. How do you think this might work? Write some pseudocode for a method heapSort(int[] a) that uses a Heap like the one above to sort an array of integers. What is the runtime of your algorithm? Is it in-place? Stable?

  3. It turns out to be possible to write an in-place version of HeapSort using a max-heap. To get you started, here’s a max-heap version of the Heap class above with a couple extra methods added. The first is a constructor that takes an array of unsorted values and sets that to be the Heap’s internal storage array:

    The second method is the heapSort() method, which sorts the values in A in-place. Implement the heapSort method.

  4. The most straightforward way to insert n elements into a heap is to call add n times, which is O(n \log n). However, it turns out to be possible to build a heap of n relements in O(n) time. There are two tricky parts to this: the algorithm to build the heap, and the analysis to show that it’s O(n). In short, the approach is to build the heap “bottom-up” instead of “top-down”.

    1. Write pseudocode to implement the following method, which could be a member of the Heap class above:

    2. Noticing that a single value is always a valid heap, write pseudocode for the following, making use of the maxHeapify method above:

    3. For a given call to maxHeapify(i), the runtime is O(\log n) where n is the number of nodes in the tree rooted at i. Although maxHeapify() makes O(n) calls to the private helper, it’s possible to show that it only does a total of O(n) work. Prove this. Hint: the analysis is similar to the analysis of the recursive height calculation in AVL trees that we saw in Lecture 11 Problem 3.