Median in a stream of integers

Given that integers are read from a data stream. Find median of elements read so for in efficient way. For simplicity assume there are no duplicates. For example, let us consider the stream 5, 15, 1, 3 …

After reading 1st element of stream - 5 -> median - 5
After reading 2nd element of stream - 5, 15 -> median - 10
After reading 3rd element of stream - 5, 15, 1 -> median - 5
After reading 4th element of stream - 5, 15, 1, 3 -> median - 4, so on...

Making it clear, when the input size is odd, we take the middle element of sorted data. If the input size is even, we pick average of middle two elements in sorted stream.

public class Solution {
    public static void runningMedian(int arr[]) {
        PriorityQueue<Integer> smaller = new PriorityQueue<>((a, b) -> b - a);
        PriorityQueue<Integer> larger = new PriorityQueue<>((a, b) -> a - b);
        for (int i = 0; i < arr.length; i++) {
            // 1st step : add to larger
            larger.add(arr[i]);
            // 2nd step : add top of larger into smaller
            smaller.add(larger.poll());
            // 3rd step : equalize sizes of both
            if (larger.size() < smaller.size())
                larger.add(smaller.poll());
            // i+1 shows actual number
            if ((i + 1) % 2 == 0)
                System.out.println((larger.peek() + smaller.peek()) / 2);
            else {
                if (larger.size() > smaller.size())
                    System.out.println(larger.peek());
                else
                    System.out.println(smaller.peek());
            }
        }
    }
}

Last updated