Java 为什么死锁不是';怎么回事?
我对僵局的行为感到困惑。 如果我先在死锁类的构造函数中编写Java 为什么死锁不是';怎么回事?,java,multithreading,deadlock,Java,Multithreading,Deadlock,我对僵局的行为感到困惑。 如果我先在死锁类的构造函数中编写a.foo(b),然后编写t.start(),那么死锁不会发生,但为什么呢 class A { synchronized void foo(B b) { String name = Thread.currentThread().getName(); System.out.println(name + " entered A.foo"); try { Thre
a.foo(b)
,然后编写t.start()
,那么死锁不会发生,但为什么呢
class A {
synchronized void foo(B b) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered A.foo");
try {
Thread.sleep(2000);
} catch (Exception e) {
System.out.println("A Interrupted");
}
System.out.println(name + " trying to call B.last()");
b.last();
}
synchronized void last() {
System.out.println("Inside A.last");
}
}
class B {
synchronized void bar(A a) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered B.bar");
try {
Thread.sleep(1000);
} catch (Exception e) {
System.out.println("B Interrupted");
}
System.out.println(name + " trying to call A.last()");
a.last();
}
synchronized void last() {
System.out.println("Inside B.last");
}
}
public class Deadlock implements Runnable {
A a = new A();
B b = new B();
Thread t;
Deadlock() {
Thread.currentThread().setName("MainThread");
t = new Thread(this, "RacingThread");
a.foo(b);
t.start();
}
public static void main(String args[]) {
new Deadlock();
}
public void run() {
b.bar(a);
}
}
要产生死锁,必须有两个进程(
a
和b
)和两个锁(x
和y
)。他们必须按照如下顺序获取锁:
获取a
李>x
获取b
李>y
正在等待获取a
李>y
正在等待获取b
x
同步的方法。他们正在获取与方法运行的实例关联的锁。也就是说,他们从不试图获得对方的锁。这就是它们被序列化的原因
要产生死锁,您需要依赖于synchronized
方法的隐式锁以外的其他锁。要产生死锁,您必须有两个进程(a
和b
)和两个锁(x
和y
)。他们必须按照如下顺序获取锁:
a
获取x
李>
b
获取y
李>
a
正在等待获取y
李>
b
正在等待获取x
在代码中,有同步的方法。他们正在获取与方法运行的实例关联的锁。也就是说,他们从不试图获得对方的锁。这就是它们被序列化的原因
要产生死锁,您需要依赖于synchronized
方法的隐式锁以外的其他锁
如果我先在类的构造函数Deadlock
中编写a.foo(b)
,然后编写t.start()
class A {
synchronized void foo(B b) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered A.foo");
try {
Thread.sleep(2000);
} catch (Exception e) {
System.out.println("A Interrupted");
}
System.out.println(name + " trying to call B.last()");
b.last();
}
synchronized void last() {
System.out.println("Inside A.last");
}
}
class B {
synchronized void bar(A a) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered B.bar");
try {
Thread.sleep(1000);
} catch (Exception e) {
System.out.println("B Interrupted");
}
System.out.println(name + " trying to call A.last()");
a.last();
}
synchronized void last() {
System.out.println("Inside B.last");
}
}
public class Deadlock implements Runnable {
A a = new A();
B b = new B();
Thread t;
Deadlock() {
Thread.currentThread().setName("MainThread");
t = new Thread(this, "RacingThread");
a.foo(b);
t.start();
}
public static void main(String args[]) {
new Deadlock();
}
public void run() {
b.bar(a);
}
}
这是因为对a.foo(b)
的调用不是异步的,因此在对a.foo(b)
的调用完成之前不会调用t.start()
如果我先在类的构造函数Deadlock
中编写a.foo(b)
,然后编写t.start()
class A {
synchronized void foo(B b) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered A.foo");
try {
Thread.sleep(2000);
} catch (Exception e) {
System.out.println("A Interrupted");
}
System.out.println(name + " trying to call B.last()");
b.last();
}
synchronized void last() {
System.out.println("Inside A.last");
}
}
class B {
synchronized void bar(A a) {
String name = Thread.currentThread().getName();
System.out.println(name + " entered B.bar");
try {
Thread.sleep(1000);
} catch (Exception e) {
System.out.println("B Interrupted");
}
System.out.println(name + " trying to call A.last()");
a.last();
}
synchronized void last() {
System.out.println("Inside B.last");
}
}
public class Deadlock implements Runnable {
A a = new A();
B b = new B();
Thread t;
Deadlock() {
Thread.currentThread().setName("MainThread");
t = new Thread(this, "RacingThread");
a.foo(b);
t.start();
}
public static void main(String args[]) {
new Deadlock();
}
public void run() {
b.bar(a);
}
}
这是因为对a.foo(b)
的调用完成后才会调用t.start()
,因为对a.foo(b)
的调用不是异步的。运行此程序时,创建的第一个线程是'main thread',因此如果在t.start()之前调用a.foo(b)),该程序将由主线程串行执行。因此,在主线程下,直到a.foo()->b.foo()的执行堆栈结束t.start()才会执行,即
以简单的方式执行,直到第4行的代码在
行号5将不被执行
。因此在a.foo(b)的情况下;t、 开始代码>死锁是不可能的。但在t.start()的情况下;a、 傅(乙);代码>异步执行将在'thread t.start()'之后不久开始,因此它会导致两个线程之间出现死锁,试图访问彼此相反的锁。运行此程序时,创建的第一个线程是'main thread',因此如果在t.start()之前调用a.foo(b),则,该程序将由主线程串行执行。因此,在主线程下,直到a.foo()->b.foo()的执行堆栈结束t.start()才会执行,即
以简单的方式执行,直到第4行的代码在
行号5将不被执行
。因此在a.foo(b)的情况下;t、 开始代码>死锁是不可能的。但在t.start()的情况下;a、 傅(乙);代码>异步执行将在'thread t.start()'之后很快开始,因此它会导致两个线程之间的死锁,试图访问彼此相反的锁。您能解释一下您认为这里发生了什么会导致死锁吗?这看起来很好…你的std输出是什么?你能解释一下你认为这里发生了什么会导致死锁吗?这看起来很好…你的性病输出是什么?谢谢。我已经解决了问题。谢谢。我已经解决了问题。