文章目录
- 死锁的概念
- 产生死锁问题的必要条件
- 如何避免死锁
有两个小朋友站在超市的零食区,手上各拿着五毛钱,他们直勾勾的看着眼前的棒棒糖,问了问阿姨,这个棒棒糖要一块钱。所以a对b说:“你把你的五毛钱给我买棒棒糖”,b不乐意了,说:“凭什么,你把你的五毛钱给我,我买棒棒糖”,然后呢,这两个小朋友就在超市一直争执,谁都不想把自己手中的五毛钱让出去。那么在这个场景中,两个小朋友就是两个线程,他们两人手上的五毛钱就相当于临界锁,棒棒糖相当于临界资源,超市的阿姨相当于OS操作系统。
死锁的概念
死锁是指在一组进程中的各个进程均占用不会释放的资源,但因互相申请被其它进程所占用的不会释放的资源而处于一种永久等待的状态。
一把锁可能产生死锁吗?
可能。程序员申请一把锁,访问临界资源,本来该释放,结果写错了,他又写成申请一把锁,所以一个执行流同时申请同一把锁,申请两次的时候,当他在第二次申请锁的时候,就挂起了,自己就把自己死锁了。所以一把锁的情况也可能出现死锁。这就是“骑驴找驴了”。
产生死锁问题的必要条件
- 互斥条件:一个资源每次只能被一个执行流使用。
- 请求与保持:一个执行流因请求资源而阻塞时,对已获得的资源保持不放。回到最开始讲的小故事,a请求b给他五毛钱,但是a手上还拿着五毛钱,即一个线程申请锁,当时它的锁还未释放,这就叫做请求和保持。
- 环路等待(循环等待条件):若干执行流之间形成一种头尾相接的循环等待资源的关系。
- 不剥夺条件:一个执行流已获得的资源,在未使用完之前,不能强行剥夺。
如何避免死锁
核心思想:破坏死锁的4个必要条件之一。
1.不加锁(破坏互斥条件)
2.主动释放锁,避免锁未释放的场景(破坏请求与保持)
3.按顺序申请锁(破坏环路等待条件)
4.控制线程统一释放锁,资源一次性分配
ps:加锁和解锁不一定非要在一个线程内进行,可以跨进程!
运行结果: