排除队列超时

时间:2016-11-07 19:32:32

标签: java multithreading queue

我有一个进程,其中多个生成器填充从此队列检索的队列和单个使用者进程数据。

为了提高效率,消费者使用BlockingQueue#drainTo API从队列中排出数据。但是有一个问题,当队列为空时,消费者会尝试在循环中耗尽数据,而不会消耗大量的CPU。

是否有API允许排除队列,其超时时间与BlockingQueue#poll(long timeout, TimeUnit unit)类似?

消费者代码示例:

while (threadIsActive) {
    List<Event> events = new ArrayList<>();
    queue.drainTo(events);
    processEvents(events);
}

2 个答案:

答案 0 :(得分:0)

我最终使用了@Kayaman建议的poll / drainTo组合,我不太喜欢它,它看起来很难看。但我会接受提出更好解决方案的任何其他答案:

while (threadIsActive) {
    Event firstEvent = queue.poll(queuePollTimeout, TimeUnit.MILLISECONDS);
    if (firstEvent != null) {
        // reserve enough space to fit first event, current queue capacity and
        // new events which occur while we are draining
        int drainCapacity = queue.size() * 2;
        List<Event> events = new ArrayList<>(drainCapacity);

        events.add(firstEvent);
        queue.drainTo(events);

        processEvents(events);
    }
}

答案 1 :(得分:-1)

我同意@Kayaman,因为BlockingQueue#drainTo API是非阻止API,因此在这种情况下,我们可以使用BlockingQueue#poll(long timeout, TimeUnit unit) API来完成您的任务。也许你可以写下面的代码:

    while (threadIsActive) {
        List<Event> events = new ArrayList<>();
        events.add(queue.poll(timeout, TimeUnit.SECONDS))  //Block until queue is EMPTY
        queue.drainTo(events);
        processEvents(events);
    }