โ† Back to Heap Pattern

๐Ÿ“š Sliding Window Median โ€“ Java Cheat Sheet

๐Ÿ“Œ What Is It?

The problem involves finding the median of every sliding window of size k in an array. The sliding window moves one step at a time, and the median of the current window is calculated.

To solve this efficiently, we use two heaps:

The heaps are balanced such that the size difference between them is at most 1. This allows us to calculate the median in constant time by looking at the top elements of the heaps.

๐Ÿงฑ Pattern Template

class Solution {
    public double[] medianSlidingWindow(int[] nums, int k) {
        PriorityQueue<Integer> maxHeap = new PriorityQueue<>(Collections.reverseOrder());
        PriorityQueue<Integer> minHeap = new PriorityQueue<>();
        Map<Integer, Integer> delayed = new HashMap<>(); // Tracks elements to be removed
        double[] result = new double[nums.length - k + 1];
        int left = 0, right = 0;

        while (right < nums.length) {
            // Add the current number to the appropriate heap
            if (maxHeap.isEmpty() || nums[right] <= maxHeap.peek()) {
                maxHeap.offer(nums[right]);
            } else {
                minHeap.offer(nums[right]);
            }

            // Balance the heaps
            balanceHeaps(maxHeap, minHeap);

            // Check if the window size is reached
            if (right - left + 1 == k) {
                // Calculate the median
                if (maxHeap.size() > minHeap.size()) {
                    result[left] = maxHeap.peek();
                } else {
                    result[left] = (maxHeap.peek() + minHeap.peek()) / 2.0;
                }

                // Remove the element going out of the window
                int toRemove = nums[left];
                delayed.put(toRemove, delayed.getOrDefault(toRemove, 0) + 1);
                if (toRemove <= maxHeap.peek()) {
                    maxHeap.poll();
                } else {
                    minHeap.poll();
                }

                // Balance the heaps after removal
                balanceHeaps(maxHeap, minHeap);

                left++; // Slide the window
            }

            right++;
        }

        return result;
    }

    private void balanceHeaps(PriorityQueue<Integer> maxHeap, PriorityQueue<Integer> minHeap) {
        while (maxHeap.size() > minHeap.size() + 1) {
            minHeap.offer(maxHeap.poll());
        }
        while (minHeap.size() > maxHeap.size()) {
            maxHeap.offer(minHeap.poll());
        }
    }
}

๐Ÿ“Š Time Complexity

โœ… Use Cases

๐Ÿ“˜ Common LeetCode Problems

๐Ÿงช Example: Sliding Window Median

Input: nums = [1,3,-1,-3,5,3,6,7], k = 3
Output: [1.0,-1.0,-1.0,3.0,5.0,6.0]

Explanation:
Sliding window size = 3
Window positions and medians:
[1, 3, -1] -> Median = 1.0
[3, -1, -3] -> Median = -1.0
[-1, -3, 5] -> Median = -1.0
[-3, 5, 3] -> Median = 3.0
[5, 3, 6] -> Median = 5.0
[3, 6, 7] -> Median = 6.0

๐Ÿ’ก Pro Tips