import heapq
# 1. heapq.heappush(heap, item)
# Adds item to the heap while maintaining heap property
heap = [1, 3, 5, 7, 9, 2]
heapq.heappush(heap, 4)
print("After heappush:", heap)
# Output: [1, 3, 2, 7, 9, 5, 4]
# 2. heapq.heappop(heap)
# Removes and returns the smallest item from the heap
smallest = heapq.heappop(heap)
print("Popped smallest:", smallest) # Output: 1
print("After heappop:", heap) # Output: [2, 3, 5, 7, 9]
# 3. heapq.heappushpop(heap, item)
# Pushes item to heap and pops and returns the smallest item
result = heapq.heappushpop(heap, 4)
print("Pushed and popped:", result) # Output: 2
print("After heappushpop:", heap) # Output: [3, 4, 5, 7, 9]
# 4. heapq.heapreplace(heap, item)
# Pops the smallest item and pushes item to heap
smallest = heapq.heapreplace(heap, 4)
print("Heap replace popped:", smallest) # Output: 3
print("After heapreplace:", heap) # Output: [4, 4, 5, 7, 9]
# 5. heapq.nlargest(n, iterable, key=None)
# Returns the n largest elements from the iterable
numbers = [1, 3, 5, 7, 9, 2]
largest = heapq.nlargest(3, numbers)
print("3 largest numbers:", largest) # Output: [9, 7, 5]
# 6. heapq.nsmallest(n, iterable, key=None)
# Returns the n smallest elements from the iterable
smallest = heapq.nsmallest(3, numbers)
print("3 smallest numbers:", smallest) # Output: [1, 2, 3]
# 7. heapq.merge(*iterables, key=None, reverse=False)
# Merges multiple sorted iterables into a single sorted iterator
list1 = [1, 3, 5]
list2 = [2, 4, 6]
merged = heapq.merge(list1, list2)
print("Merged lists:", list(merged)) # Output: [1, 2, 3, 4, 5, 6]
# Simulating a Max-Heap (by negating the values)
heap = []
heapq.heappush(heap, -10)
heapq.heappush(heap, -5)
heapq.heappush(heap, -15)
print("Max heap simulation:", [-x for x in heap]) # Output: [15, 5, 10]
# Popping the largest element in the simulated max-heap
max_value = -heapq.heappop(heap)
print("Popped max value:", max_value) # Output: 15
print("After popping:", [-x for x in heap]) # Output: [10, 5]
# Explanation of heapq functions:
# - heapq.heappush(heap, item) - Push item onto heap
# - heapq.heappop(heap) - Pop smallest item from heap
# - heapq.heappushpop(heap, item) - Push item, then pop smallest item
# - heapq.heapreplace(heap, item) - Pop smallest item, then push item
# - heapq.nlargest(n, iterable) - Get the n largest elements
# - heapq.nsmallest(n, iterable) - Get the n smallest elements
# - heapq.merge(*iterables) - Merge multiple sorted iterables into one