Condition 接口(interface)的文档内部: http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/locks/Condition.html
有一个使用该条件的示例类。我将复制/粘贴到此处:
class BoundedBuffer {
final Lock lock = new ReentrantLock();
final Condition notFull = lock.newCondition();
final Condition notEmpty = lock.newCondition();
final Object[] items = new Object[100];
int putptr, takeptr, count;
public void put(Object x) throws InterruptedException {
lock.lock();
try {
while (count == items.length)
notFull.await();
items[putptr] = x;
if (++putptr == items.length) putptr = 0;
++count;
notEmpty.signal();
} finally {
lock.unlock();
}
}
public Object take() throws InterruptedException {
lock.lock();
try {
while (count == 0)
notEmpty.await();
Object x = items[takeptr];
if (++takeptr == items.length) takeptr = 0;
--count;
notFull.signal();
return x;
} finally {
lock.unlock();
}
}
}
我不明白的是,这如何能够在不造成死锁的情况下工作(注意:我没有测试它,我只是假设它有效)?
如果我调用 BoundedBuffer.put 一百次,那么在第一百次时,它将被阻塞在 notFull.await() 方法中,并且这将处于锁定状态。 如果我然后从另一个线程执行 BoundedBuffer.take() 那么我应该被阻塞在 lock.lock() 的第一行。
我在这里遗漏了什么吗?
最佳答案
是的,你确实错过了一些东西。来自 JavaDoc :
The key property that waiting for a condition provides is that it atomically releases the associated lock and suspends the current thread, just like Object.wait.
因此,当调用 await()
时,锁就会被释放。
来自 await()
方法本身的 JavaDoc:
void await() throws InterruptedException
Causes the current thread to wait until it is signalled or interrupted. The lock associated with this Condition is atomically released and the current thread becomes disabled for thread scheduling purposes and lies dormant until one of four things happens:
并且方法signal()
会唤醒一个线程,该线程将在继续之前重新获取锁。来自方法 signal()
的 JavaDoc:
void signal()
Wakes up one waiting thread. If any threads are waiting on this condition then one is selected for waking up. That thread must then re-acquire the lock before returning from await.
关于Java java.util.concurrent.locks.Condition 接口(interface)文档,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23263486/