没有等待线程的信号条件

时间:2014-08-09 15:01:43

标签: java multithreading signals race-condition reentrantlock

我使用ReentrantLockCondition来同步两个线程。每当消费者线程在生产者线程执行await()之前对条件执行signal()时,事情似乎正常。但是,当生产者线程在使用者线程执行signal()之前执行await()时,消费者线程最终会等待永远。这应该发生还是我做错了什么?发出条件并且没有等待线程时,预期的行为是什么?

这是消费者的代码:

this.lock.lock();
Log.d("websocket", "Sender acquired lock");
try
{
    Log.d("websocket", "Sender waiting for message from server");
    this.resultReady.await();
    Log.d("websocket", "Sender waking up");
    return this.result;

} catch (InterruptedException e)
{
    e.printStackTrace();
}
finally {
    this.lock.unlock();
}

这是制作人的代码:

Log.d("websocket", "Receiver acquiring lock");
this.lock.lock();
Log.d("websocket", "Receiver acquired lock");
try
{
    Log.d("websocket", "Receiver setting result");
    result = serviceResult;
    Log.d("websocket", "Receiver waking up waiting threads");
    this.resultReady.signal();
} finally
{
    this.lock.unlock();
}

1 个答案:

答案 0 :(得分:2)

  

这应该发生还是我做错了什么?是什么   条件发出信号且没有条件时的预期行为   等待线程?

那应该发生。如果没有线程在等待,那就没有效果了。 Java doc说:

  

唤醒一个等待线程。

     

如果有任何线程正在等待这个条件,则选择一个   起来。然后该线程必须在返回之前重新获取锁   等待。

当然,如果没有线程可以唤醒,那么没有效果吗?

你有一个缓冲区,其中包含一个项目result。您必须独立于await()方法测试此结果是否有效。或者切换到类似Semaphore的东西,它具有你可以设置的内部状态。

// Consumer
this.lock.lock();
Log.d("websocket", "Sender acquired lock");
try
{
    Log.d("websocket", "Sender waiting for message from server");
    while( result == null )   // CHANGE HERE
        resultReady.await();
    Log.d("websocket", "Sender waking up");
    return this.result;

} catch (InterruptedException e)
{
    e.printStackTrace();
}
finally {
    this.lock.unlock();
}