死锁发生的条件
1、互斥条件:任意时刻该资源只由一个线程占用
2、请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放
3、线程已获得的资源在末使用完之前不能被其他线程强行剥夺,只有自己使用完毕后才释放资源。
4、循环等待条件:若干进程之间形成一种头尾相接的循环等待资源关系
避免死锁只需破坏以上4个条件之一即可。
如果资源可以共享就不会发生死锁。但是有些资源根本不能同时访问,比如打印机等临界资源,所以破坏互斥条件不太可行。
死锁代码
public class DeadLock {
public static void main(String[] args) {
Object a = new Object();
Object b = new Object();
new Thread(new Runnable() {
@Override
public void run() {
synchronized (a) {
System.out.println("等待b");
try {
//这里sleep10s是为了让线程BB拿到资源b
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
synchronized (b) {
}
}
}
}, "AA").start();
new Thread(new Runnable() {
@Override
public void run() {
synchronized (b) {
System.out.println("等待a");
synchronized (a) {
}
}
}
}, "BB").start();
}
}
运行上面程序,然后使用jps命令,输出如下:
然后使用jstack命令查看堆栈信息,jstack 17332,输出如下
从控制台的输出可以看到的确发生了死锁。