深圳市手机网站建设品牌,青岛网站建,建设局建筑电工证查询网站,策划公司广告费1.什么是死锁
简单来说就是一个线程加锁后解锁不了
一个线程#xff0c;一把锁#xff0c;线程连续加锁两次。如果这个锁是不可重入锁#xff0c;会死锁。两个线程#xff0c;两把锁。
举几个例子#xff0c;1.钥匙锁车里了#xff0c;车钥匙锁家里了。2. 现在有一本书…
1.什么是死锁
简单来说就是一个线程加锁后解锁不了
一个线程一把锁线程连续加锁两次。如果这个锁是不可重入锁会死锁。两个线程两把锁。
举几个例子1.钥匙锁车里了车钥匙锁家里了。2. 现在有一本书和一支笔A拿到书B拿到笔A说你把笔给我我用完再把书给你B说你把书给我我用完笔给你。这个场景就相持不下了。
public static void main(String[] args) {Object locker1 new Object();Object locker2 new Object();Thread t1 new Thread(()- {synchronized (locker1) {System.out.println(t1线程获取Locker1);synchronized (locker2) {System.out.println(t1线程获取locker2);}}});Thread t2 new Thread(() - {synchronized (locker2) {System.out.println(t2线程尝试获取locker2);synchronized (locker1) {System.out.println(t2线程尝试获取locker1);}}});t1.start();t2.start();
}上面代码就是两线程两个锁造成了死锁。
多个线程多把锁。
一个典型模型就是哲学家就餐问题每个哲学家只会做两件事1.思考人生啥也不干阻塞等待2.吃意大利面先拿起左手的筷子再拿起右手筷子。如图两个哲学家中间放一根筷子当所有哲学家都拿起左边筷子时想要再拿右边筷子发现没筷子拿了造成死锁。
2. 出现死锁的四个必要条件
互斥锁A被线程1占有线程2就没办法占有不可抢占锁A被线程1占有线程2不能直接把锁A抢过来阻塞等待请求和保存有多把锁线程1拿到锁A之后不想释放锁还想拿锁B循环等待线程1等待线程2释放锁线程2等待线程3释放锁线程3等待线程1释放锁
3.避免死锁的方案
只要打破上面四个必要条件任意一个即可解决。由于互斥和不可抢占是内核决定的无法改变。打破请求和保持适用场景不多要看需要场景是否允许。打破循环依赖约定好加锁顺序就可以打破。像t1线程加锁顺序是locker1,locker2;t2线程加锁顺序是locker2,locker1这就导致循环依赖。如果我们给锁编号约定加多个锁的时候必须先加编号小的锁后加编号大的锁就能有效避免循环等待了。