螺纹阻塞问题,需要澄清

时间:2012-02-05 01:22:22

标签: java multithreading

使用BlockingQueue时,我实现了以下逻辑从中读取,直到另有说明。不幸的是,间歇性地发生了以下情况:

问题:

  • 即使在shouldContinueReading设置为false之后,循环也不会一直中断
  • 问题是间歇性的,有时候一切正常

作为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?我没有正确宣布它吗?

1 个答案:

答案 0 :(得分:1)

我敢打赌QThread.shouldContinueReading = false;总是没有被执行,或者读取线程没有首先执行。即你看到的问题很可能是在流的某个地方 - 而不是在这里。我要做的第一件事就是确定问题的确切位置,100%放心(增加一些印刷语句)。

除了这个问题,我建议使用线程中断机制而不是滚动你自己的旗帜(这反过来只是一个美化的旗帜,但这样你可以影响第三方代码,如BlockedQueue并使实现更简单,更高效,尤其是如果这是生产代码。