使用BlockingQueue
时,我实现了以下逻辑从中读取,直到另有说明。不幸的是,间歇性地发生了以下情况:
问题:
作为QThread类的一部分,我声明:
public static volatile boolean shouldContinueReading = true;
运行(确认执行)方法包含:
while (shouldContinueReading) {
try {
String retrieved = qIn.poll(2, TimeUnit.MILLISECONDS);
if (retrieved != null)
consume(retrieved);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println("I am out"); // <-- not always seen
if (qIn.remainingCapacity() > 0) {
try {
consume(qIn.take());
} catch (InterruptedException e) {
e.printStackTrace();
}
}
当这种情况发生时,在另一个线程中,当某些事情发生时,shouldContinueReading
会改变状态
while (stillReading) {
// do nothing
}
QThread.shouldContinueReading = false;
原来问题还有一点:
private void consume(String take) {
// some processing
produce(newData.toString());
}
private void produce(String newData) {
System.out.println(newData);
try {
qOut.put(newData); // <-- Problem is here. Should use offer instead of put
} catch (InterruptedException e) {
e.printStackTrace();
}
}
qIn(队列输入)和qOut(队列输出)都声明为:
private volatile BlockingQueue<String> qIn;
private volatile BlockingQueue<String> qOut;
对象本身在其他地方创建如下,并传递给构造函数:
BlockingQueue<String> q1 = new SynchronousQueue<String>();
BlockingQueue<String> q2 = new SynchronousQueue<String>();
QThread qThread = new QThread(q1, q2);
有什么建议吗?我应该怎么做qOut?我没有正确宣布它吗?
答案 0 :(得分:1)
我敢打赌QThread.shouldContinueReading = false;
总是没有被执行,或者读取线程没有首先执行。即你看到的问题很可能是在流的某个地方 - 而不是在这里。我要做的第一件事就是确定问题的确切位置,100%放心(增加一些印刷语句)。
除了这个问题,我建议使用线程中断机制而不是滚动你自己的旗帜(这反过来只是一个美化的旗帜,但这样你可以影响第三方代码,如BlockedQueue
并使实现更简单,更高效,尤其是如果这是生产代码。