===== ISTEM =====
Solve the following programming task.

TASK: Median Finder on a Data Stream

Write a 'MedianFinder' class that accepts numbers from a data stream and computes the running median with O(log n) insertion and O(1) lookup. It must have 'add_num(num)' and 'find_median()' methods.

STARTER CODE (python):
class MedianFinder:
    def __init__(self):
        pass
    def add_num(self, num: int) -> None:
        pass
    def find_median(self) -> float:
        pass


RULES:
- Keep the function name and signature EXACTLY as given.
- Return working code only. No explanations.
- Put the code in a single ``` block.
- Try to solve it first. If you genuinely cannot, write only this single
  line instead of producing faulty code: CANNOT_SOLVE

===== HAM YANIT =====
```python
import heapq

class MedianFinder:
    def __init__(self):
        self.max_heap = []  # max heap (invert values)
        self.min_heap = []  # min heap

    def add_num(self, num: int) -> None:
        # Insert into appropriate heap
        if not self.max_heap or num <= -self.max_heap[0]:
            heapq.heappush(self.max_heap, -num)
        else:
            heapq.heappush(self.min_heap, num)

        # Rebalance heaps so that len difference <= 1
        if len(self.max_heap) > len(self.min_heap) + 1:
            heapq.heappush(self.min_heap, -heapq.heappop(self.max_heap))
        elif len(self.min_heap) > len(self.max_heap) + 1:
            heapq.heappush(self.max_heap, -heapq.heappop(self.min_heap))

    def find_median(self) -> float:
        if len(self.max_heap) > len(self.min_heap):
            return float(-self.max_heap[0])
        if len(self.min_heap) > len(self.max_heap):
            return float(self.min_heap[0])
        if not self.max_heap and not self.min_heap:
            return 0.0  # no elements added yet
        return (-self.max_heap[0] + self.min_heap[0]) / 2.0
```