/// <summary>Removes the entry at the top of the heap.</summary> /// <returns>The removed entry.</returns> public virtual object Remove() { // Get the first item and save it for later (this is what will be returned). if (_list.Count == 0) { throw new InvalidOperationException("Cannot remove an item from the heap as it is empty."); } object toReturn = ((ChoBinaryHeapEntry)_list[0]).Value; // Remove the first item _list.RemoveAt(0); // See if we can stop now (if there's only one item or we're empty, we're done) if (_list.Count > 1) { // Move the last element to the beginning _list.Insert(0, _list[_list.Count - 1]); _list.RemoveAt(_list.Count - 1); // Start reheapify int current = 0, possibleSwap = 0; // Keep going until the tree is a heap while (true) { // Get the positions of the node's children int leftChildPos = 2 * current + 1; int rightChildPos = leftChildPos + 1; // Should we swap with the left child? if (leftChildPos < _list.Count) { // Get the two entries to compare (node and its left child) ChoBinaryHeapEntry entry1 = (ChoBinaryHeapEntry)_list[current]; ChoBinaryHeapEntry entry2 = (ChoBinaryHeapEntry)_list[leftChildPos]; // If the child has a higher key than the parent, set that as a possible swap if (entry2.CompareTo(entry1) > 0) { possibleSwap = leftChildPos; } } else { break; // if can't swap this, we're done } // Should we swap with the right child? Note that now we check with the possible swap // position (which might be current and might be left child). if (rightChildPos < _list.Count) { // Get the two entries to compare (node and its left child) ChoBinaryHeapEntry entry1 = (ChoBinaryHeapEntry)_list[possibleSwap]; ChoBinaryHeapEntry entry2 = (ChoBinaryHeapEntry)_list[rightChildPos]; // If the child has a higher key than the parent, set that as a possible swap if (entry2.CompareTo(entry1) > 0) { possibleSwap = rightChildPos; } } // Now swap current and possible swap if necessary if (current != possibleSwap) { object temp = _list[current]; _list[current] = _list[possibleSwap]; _list[possibleSwap] = temp; } else { break; // if nothing to swap, we're done } // Update current to the location of the swap current = possibleSwap; } } // Return the item from the heap return(toReturn); }