Live coding puzzles question 172 of 180 mid
Implement a bounded blocking queue with wait and notify.
- Wrap an
ArrayListinsynchronized - Correct: A ring buffer or deque guarded by one monitor, with
while (full) wait()in put,while (empty) wait()in take, andnotifyAllafter each - Use
Collections.synchronizedListand poll in a loop - Use a
ConcurrentLinkedQueueand check the size
class BoundedQueue<T> {
private final Queue<T> items = new ArrayDeque<>();
private final int capacity;
BoundedQueue(int capacity) {
this.capacity = capacity;
}
synchronized void put(T item) throws InterruptedException {
while (items.size() == capacity) {
wait();
}
items.add(item);
notifyAll();
}
synchronized T take() throws InterruptedException {
while (items.isEmpty()) {
wait();
}
T item = items.remove();
notifyAll();
return item;
}
}
Expect the follow-up: why notifyAll and not notify? Because producers and consumers wait on the
same monitor, so notify can wake a producer when only a consumer can proceed, and the wakeup is lost.
The better version uses a ReentrantLock with two Conditions, notFull and notEmpty, so each
signal reaches a thread that can actually run. That is exactly what ArrayBlockingQueue does.