java并发-死锁

本文讲解死锁的概念和示例。

死锁是什么

死锁描述了两个或多个线程永远被阻塞,等待彼此的情况。当多个线程需要相同的锁但以不同的顺序获取它们时,会发生死锁。

代码示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
/**
* 演示死锁的由来:因为线程加锁的顺序不一致导致,相互等待对方持有的锁,形成死锁
*
* @author jimo
* @date 2018/9/29 13:46
*/
public class DeadLockDemo {
private final static Object LOCK1 = new Object();
private final static Object LOCK2 = new Object();

public static void main(String[] args) {
new ThreadDemo1().start();
new ThreadDemo2().start();
}

private static class ThreadDemo1 extends Thread {
@Override
public void run() {
synchronized (LOCK1) {
System.out.println("线程1持有lock1...");

try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println("线程1等待lock2");

synchronized (LOCK2) {
System.out.println("线程1持有lock1和lock2");
}
}
}
}

private static class ThreadDemo2 extends Thread {
@Override
public void run() {
synchronized (LOCK2) {
System.out.println("线程2持有lock2...");

try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println("线程2等待lock1");

synchronized (LOCK1) {
System.out.println("线程2持有lock1和lock2");
}
}
}
}
}

运行结果:

改正确

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
/**
* 演示死锁的由来:因为线程加锁的顺序不一致导致,相互等待对方持有的锁,形成死锁
*
* @author jimo
* @date 2018/9/29 13:46
*/
public class DeadLockDemo {
private final static Object LOCK1 = new Object();
private final static Object LOCK2 = new Object();

public static void main(String[] args) {
new ThreadDemo1().start();
new ThreadDemo2().start();
}

private static class ThreadDemo1 extends Thread {
@Override
public void run() {
synchronized (LOCK1) {
System.out.println("线程1持有lock1...");

try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println("线程1等待lock2");

synchronized (LOCK2) {
System.out.println("线程1持有lock1和lock2");
}
}
}
}

private static class ThreadDemo2 extends Thread {
@Override
public void run() {
synchronized (LOCK1) {
System.out.println("线程2持有lock1...");

try {
Thread.sleep(10);
} catch (InterruptedException e) {
}
System.out.println("线程2等待lock2");

synchronized (LOCK2) {
System.out.println("线程2持有lock1和lock2");
}
}
}
}
}

结果: