概述
LockSupport是一个非常方便实用的线程阻塞工具,它可以在线程内任意位置让线程阻塞。和Thread.suspend()
相比,它弥补了由于resume()
在前发生,导致线程无法继续执行的情况。和Object.wait()
方法相比,它不需要先获得某个对象的锁,也不会抛出InterruptedException异常。
park()
可以阻塞当前线程,其中每一个线程都有一个许可,该许可默认为[不可用] 。
如果该许可是 [可用] 状态,那么park()
方法会立即返回,消费这个许可,将该许可变更为 [不可用] 状态,流程代码可以继续执行。
如果该许可是 [不可用] 状态,那么park()
方法将会阻塞;unpark()
方法,会将指定线程的一个许可变为 [可用] 状态;
举例解释
为了便于大家理解,我们可以举一个场景,就是A同学想要去食堂打饭(买汉堡),那么这个A同学就相当于我们的线程了。
情况1: 当A同学去取汉堡(调用park()方法
)的时候,如果取餐台没有汉堡(即:许可为【不可用】状态),则他需要等待(线程阻塞);
情况2: 当A同学去取汉堡(调用park()方法
)的时候,如果取餐台有汉堡(即:许可为【可用】状态),则他拿走汉堡去吃饭,取餐台又没有汉堡了(许可从【可用】变为【不可用】状态)
情况3: 当服务员打算去补餐(调用unpark()方法
)的时候,发现取餐台没有汉堡(即:许可为【不可用】状态),则他去后厨拿来一个汉堡,放到取餐台上(许可从【不可用】变为【可用】状态)
情况4: 当服务员打算去补餐(调用unpark()方法
)的时候,发现取餐台已经有汉堡了(即:许可为【可用】状态),则他就去做别的事情了
为了方便大家理解,请见如下所示:
代码示例
示例一: 先执行 unpark() 方法再执行 park() 方法,也不会造成永久卡死线程。如下所示:
示例二: LockSupport.park()还能支持中断。但是它不会抛InterruptedException异常。它只会默默的返回,但是我们可以从Thread.interrupted()等方法获得中断标记。
今天的文章内容就这些了:
写作不易,笔者几个小时甚至数天完成的一篇文章,只愿换来您几秒钟的点赞&分享。
更多技术干货,欢迎大家关注公众号“爪哇缪斯” ~ (^o^)/ ~ 「干货分享,每天更新」