[英]Why is the order in which notify() is called in the following blocking queue example important?
我针对Prod-Cons问题编写了一个简单的Blocking Queue示例。 下面的示例无效。 除非我在等待线程上用通知交换入队/出队逻辑的添加/删除部分。 我在BlockingQueue的任何实现中都找不到对此行为的明确解释。 在入队部分中,添加元素然后进行通知是否正确? 这样,我可以保证,当Consumer线程运行时,它应该有一个消费者元素,并且不会返回null。 请解释。
import java.util.LinkedList;
import java.util.Queue;
public class BlockingQueueCustom<T> {
private int size = 10;
private Queue<T> queue = new LinkedList<T>();
public BlockingQueueCustom(int s) {
this.size = s;
}
public synchronized void enqueue(T element) throws InterruptedException {
while (queue.size() == size) {
wait();
}
queue.add(element); //Comment this part to make it work
if (queue.size() == 0) {
this.notifyAll();
}
//queue.add(element); Uncommenting this will make it work
}
public synchronized T dequeue() throws InterruptedException {
while (queue.size() == 0) {
this.wait();
}
T element = queue.remove(); //Comment this part to make it work
if (queue.size() == size) {
this.notifyAll();
}
return element; //Comment this part to make it work
//return queue.remove(); Uncommenting this will make it work
}
}
在入队部分中,添加元素然后进行通知是否正确?
这部分并不重要,因为您使用的是同步方法-除非您仍然退出enqueue
方法,否则其他线程将无法运行。 但是,对于size()
的测试确实很重要。 看这里:
if (queue.size() == 0)
如果刚刚添加了元素,您如何期望这是正确的? 您可以检查它是否为1,这意味着在添加元素之前 ,它必须为0。或者可以保留一个单独的变量:
boolean shouldNotify = queue.size() == 0;
queue.add(element);
if (shouldNotify) {
this.notifyAll();
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.