Min-Heap (Priority Queue)
Intuition
We can simulate room allocation using a min-heap that tracks the end times of ongoing meetings. Sort the meetings by start time, then process each meeting in order. For each meeting, check if the earliest-ending meeting (heap top) has already finished. If so, that room can be reused -- pop it from the heap. Then push the current meeting's end time onto the heap. The heap size at any point represents the number of rooms in use. The maximum heap size during the process is the answer.
Algorithm
- Sort the intervals by start time.
- Initialize a min-heap. Push the end time of the first meeting.
- For each subsequent meeting:
- The size of the heap at the end is the minimum number of rooms required.
O(n log n)SpaceO(n)Code (C++ · Java · Python · Go)
class Solution {
public:
int minMeetingRooms(vector<vector<int>>& intervals) {
sort(intervals.begin(), intervals.end());
priority_queue<int, vector<int>, greater<int>> minHeap;
for (auto& interval : intervals) {
if (!minHeap.empty() && minHeap.top() <= interval[0]) {
minHeap.pop();
}
minHeap.push(interval[1]);
}
return minHeap.size();
}
};class Solution {
public int minMeetingRooms(int[][] intervals) {
Arrays.sort(intervals, (a, b) -> a[0] - b[0]);
PriorityQueue<Integer> minHeap = new PriorityQueue<>();
for (int[] interval : intervals) {
if (!minHeap.isEmpty() && minHeap.peek() <= interval[0]) {
minHeap.poll();
}
minHeap.offer(interval[1]);
}
return minHeap.size();
}
}import heapq
def minMeetingRooms(intervals: List[List[int]]) -> int:
intervals.sort()
heap = []
for start, end in intervals:
if heap and heap[0] <= start:
heapq.heappop(heap)
heapq.heappush(heap, end)
return len(heap)import (
"container/heap"
"sort"
)
type IntHeap []int
func (h IntHeap) Len() int { return len(h) }
func (h IntHeap) Less(i, j int) bool { return h[i] < h[j] }
func (h IntHeap) Swap(i, j int) { h[i], h[j] = h[j], h[i] }
func (h *IntHeap) Push(x interface{}) { *h = append(*h, x.(int)) }
func (h *IntHeap) Pop() interface{} {
old := *h
n := len(old)
val := old[n-1]
*h = old[:n-1]
return val
}
func minMeetingRooms(intervals [][]int) int {
sort.Slice(intervals, func(i, j int) bool {
return intervals[i][0] < intervals[j][0]
})
h := &IntHeap{}
heap.Init(h)
for _, interval := range intervals {
if h.Len() > 0 && (*h)[0] <= interval[0] {
heap.Pop(h)
}
heap.Push(h, interval[1])
}
return h.Len()
}