yan*_*976 5 java concurrency java-8
我正在寻找一个队列,它与java.util.concurrent.BlockingQueue. 它的界面将包括:
public interface AsynchronousBlockingQueue<E> {
// - if the queue is empty, return a new CompletableFuture,
// that will be completed next time `add` is called
// - if the queue is not empty, return a completed CompletableFuture,
containing the first element of the list
public CompletableFuture<E> poll();
// if polling is in progress, complete the ongoing polling CompletableFuture.
// otherwise, add the element to the queue
public synchronized void add(E element);
}
Run Code Online (Sandbox Code Playgroud)
如果这很重要,那么应该只有一个轮询线程,并且轮询应该按顺序进行(poll轮询已经在进行时不会被调用)。
我希望它已经存在于 JVM 中,但我找不到它,当然我宁愿使用 JVM 中的东西而不是自己编写它。
另一个限制是,我被 Java 8 困住了(尽管我绝对有兴趣了解更新版本中存在的内容)。
所以最后我写了自己的课程...对评论感兴趣:)
import java.util.LinkedList;
import java.util.Queue;
import java.util.concurrent.CompletableFuture;
public class AsynchronousBlockingQueue<E> {
CompletableFuture<E> incompletePolling = null;
Queue<E> elementsQueue = new LinkedList<>();
// if the queue is empty, return a new CompletableFuture, that will be completed next time `add` is called
// if the queue is not empty, return a completed CompletableFuture containing the first element of the list
public synchronized CompletableFuture<E> poll() {
// polling must be done sequentially, so this shouldn't be called if there is a poll ongoing.
if (incompletePolling != null)
throw new IllegalStateException("Polling is already ongoing");
if (elementsQueue.isEmpty()) {
incompletePolling = new CompletableFuture<>();
return incompletePolling;
}
CompletableFuture<E> result = new CompletableFuture<>();
result.complete(elementsQueue.poll());
return result;
}
// if polling is in progress, complete the ongoing polling CompletableFuture.
// otherwise, add the element to the queue
public synchronized void add(E element) {
if (incompletePolling != null) {
CompletableFuture<E> result = incompletePolling;
// removing must be done first because the completion could trigger code that needs the queue state to be valid
incompletePolling = null;
result.complete(element);
return;
}
elementsQueue.add(element);
}
}
Run Code Online (Sandbox Code Playgroud)