我是 Java 新手,发现了此链接:http://tutorials.jenkov.com/java-concurrency/slipped-conditions.html同时了解java中的多线程。
在本教程中,以下代码被称为避免出现滑倒情况的良好实践:
public class Lock {
private boolean isLocked = true;
public void lock(){
synchronized(this){
while(isLocked){
try{
this.wait();
} catch(InterruptedException e){
//do nothing, keep waiting
}
}
isLocked = true;
}
}
public synchronized void unlock(){
isLocked = false;
this.notify();
}
}
我的疑问是,如果两个线程 A 和 B 同时调用 lock() 并且 isLocked 为 true,即锁已被其他线程 C 占用。现在:
--1 A 首先进入同步块(synchronized block)(因为只有一个人可以获得监视对象 this 的锁并进入同步块(synchronized block)) --2 A 调用 this.wait() 并释放此监视器对象上的锁(wait() 调用释放监视器对象 http://tutorials.jenkov.com/java-concurrency/thread-signaling.html#wait-notify 上的锁),但仍保留在同步块(synchronized block)内 --3 现在B进入同步块(synchronized block)(因为A已经释放了对monitor-object this的锁定) --4 B 调用 this.wait() 并释放此监视器对象上的锁(wait() 调用释放监视器对象上的锁) --5 此时线程C调用unlock()即设置isLocked为false并调用this.notify() --6 现在A和B其中之一出来wait(),然后退出while循环并设置isLocked为true --7 循环继续
那么在--3中,A和B同时位于一个同步块(synchronized block)内,这是否违反了同步块(synchronized block)内一次只能有一个线程的多线程基本原则?
请澄清我的疑问。
最佳答案
如果线程重新获取了其正在等待的对象的锁,则它只能从 wait() 方法返回。在您的场景中,A 和 B 会竞争获取锁,只有其中一个会获取锁,而另一个会一直等待,直到锁再次释放。
来自the javadoc (强调我的):
The current thread must own this object's monitor. The thread releases ownership of this monitor and waits until another thread notifies threads waiting on this object's monitor to wake up either through a call to the notify method or the notifyAll method. The thread then waits until it can re-obtain ownership of the monitor and resumes execution.
关于java - 多个线程不能同时进入同步块(synchronized block)吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27764392/