I need an Object
to be asynchronously notified when some BlockingQueue
has got an item to give.
I've searched both Javadoc and the web for a pre-made solution, then I ended up with a (maybe naive) solution of mine, here it is:
interface QueueWaiterListener<T> {
public void itemAvailable(T item, Object cookie);
}
and
class QueueWaiter<T> extends Thread {
protected final BlockingQueue<T> queue;
protected final QueueWaiterListener<T> listener;
protected final Object cookie;
public QueueWaiter(BlockingQueue<T> queue, QueueWaiterListener<T> listener, Object cookie) {
this.queue = queue;
this.listener = listener;
this.cookie = cookie;
}
public QueueWaiter(BlockingQueue<T> queue, QueueWaiterListener<T> listener) {
this.queue = queue;
this.listener = listener;
this.cookie = null;
}
@Override
public void run() {
while (!isInterrupted()) {
try {
T item = queue.take();
listener.itemAvailable(item, cookie);
} catch (InterruptedException e) {
}
}
}
}
Basically, there's a thread blocking on a take()
operation of a queue that callbacks a listener object everytime a take()
operation succeeds, optionally sending back a special cookie
object (ignore it if you want).
Question is: is there any better way to do this? Am I doing some unforgivable mistake (both in concurrency/efficiency and/or code cleanness)? Thanks in advance.
Perhaps you could subclass some BlockingQueue
(such as ArrayBlockingQueue
or LinkedBlockingQueue
or what ever you're using), add support for listeners and do
@Override
public boolean add(E o) {
super.add(o);
notifyListeners(o);
}