我正在关注有关并发性的oracle文档,在deadlock section中,他们使用以下示例。问题是我不太了解为什么会导致死锁。
正如我所看到的,这就是我正在发生的事情:
bow
方法的锁定bow
方法,进入bowBack
,释放了第一个锁并获得了第二个锁。但是我一定是错的,因为如果您运行代码,则会导致死锁……我在这里错过了什么?
非常感谢!
public class Deadlock
{
public static void main(String[] args)
{
final Friend alphonse = new Friend("Alphonse");
final Friend gaston = new Friend("Gaston");
new Thread(() -> alphonse.bow(gaston)).start();
new Thread(() -> gaston.bow(alphonse)).start();
}
static class Friend
{
private final String name;
Friend(final String name)
{
this.name = name;
}
String getName()
{
return name;
}
synchronized void bow(final Friend bower)
{
System.out.printf("%s: %s has bowed to me!%n", this.name, bower.getName());
bower.bowBack(this);
}
synchronized void bowBack(final Friend bower)
{
System.out.printf("%s: %s has bowed back to me!%n", this.name, bower.getName());
}
}
}
答案 0 :(得分:4)
假设两个线程都位于bow
行的System.out.printf
中。当他们尝试调用bowBack
时,他们都需要在bow
返回并释放锁之前获取另一个实例的锁。
由于两个线程都被锁定,等待彼此解锁,所以这是一个死锁。
答案 1 :(得分:1)
Alphonse离开了bow方法,进入bowBack,释放了第一个锁并获得了第二个锁。
这是您的问题-从bowBack
调用bow
时不会释放锁,但是现在您还需要获取另一个对象的锁。只能在您退出bow
方法时退出锁,只有在退出从其调用的bowBack
方法后,锁才会发生。