显式锁
显式锁,即Java接口Lock,ReentranLock是其中的一个实现,与synchronized一样具有可重入的特性,同时具有可以自定义公平性,可轮询,可定时,可中断的高级特性。是Java 5.0之后引入用于调节共享对象访问的机制。Java 6.0之后,synchronized做了很多优化,其性能和显示锁差异不大,因此在使用时,只有用到显示锁的高级特性才使用显示锁,特别是因为显示锁需要手动释放,所以具有一定的隐患。下面对显示锁可响应中断的高级特性进行测试。
不可中断的阻塞
在Java中,不可中断的阻塞可分为以下几类
- java.io包中的同步Socket I/O
- java.io包中的同步I/O
- Selector的异步I/O
- 获取某个锁
获取锁就是不可中断的阻塞,但是通过ReentranLock的lockInterruptibly()方法获取锁,是可以中断的,下面通过代码测试一下。思路即构造两个线程,通过请求互斥的条件达到死锁状态,获取锁时分别使用lock()和lockInterruptibly(),最后发现使用lock()来获取锁,阻塞时无法中断,而使用lockInterruptibly()获取锁,阻塞是可以中断的。
1 | public class ReentrantLockTest{ |
运行结果
如果线程0使用lockInterruptibly()来获取锁,可以看到阻塞后调用中断方法时它会主动中断,然后释放锁,让线程1得以完成,但是使用lock()来获取锁,则不会响应中断,最后请求互斥形成死锁。