可重入锁
的意思是当线程获取到锁后,再次获取锁不会出现死锁。
构造方法
这是创建了新的 ReentrantLock 对象,在 new ReentrantLock() 的时候,如果不给这个对象的构造函数赋值,它的底层会默认为 公平锁
,如果赋值 true 也是 公平锁
,当赋值是 false 时就是 非公平锁
。
这里简单讲一下 公平锁
和 非公平锁
的区别:
公平锁:
假设有 5 个线程都在获取锁,1 号线程先到,2 号线程第二个到,3 号线程第三个到,以此类推,那么第一个到的是能够先拿到这把锁的,但是呢,当 1 号线程释放掉它拿的这把锁后,2、3、4、5 号线程会按照他们到的顺序,公平
的拿到这把锁。
非公平锁:
还是上述的那 5 个线程,当 1 号线程释放掉锁以后,2、3、4、5 号线程不会按照他们到的顺序去获取锁,而是会抢,谁抢到算谁的。
// 公平锁
ReentrantLock lock = new ReentrantLock();
// 公平锁
ReentrantLock lock1 = new ReentrantLock(true);
// 非公平锁
ReentrantLock lock2 = new ReentrantLock(false);
获取锁…释放锁
lock.lock()
方法就能够拿到一把锁,但是当你获取锁的时候,必须要跟 try finally
上方第一行,并且在 finally
中要释放锁 lock.unlock()
,不然就会出现死锁。
ReentrantLock lock = new ReentrantLock();
// 获取锁
lock.lock();
try {
} finally {
// 释放锁
lock.unlock();
}
尝试获取锁
lock.tryLock()
方法就是尝试获取到这把锁,如果获取到就返回 true
,没有获取到就返回 false
,下面是一个小示例:
ReentrantLock lock = new ReentrantLock();
// 尝试获取锁
if (lock.tryLock()) {
// 获取锁成功
try {
} finally {
lock.unlock();
}
} else {
// 获取锁失败
}
lock.tryLock()
方法还有一种用法就是在一段时间内尝试获取锁,如果在一段时间内获取到了锁就返回 true
,没获取到就返回 false
。
ReentrantLock lock = new ReentrantLock();
try {
// 尝试在两秒中获取锁
if (lock.tryLock(2000, TimeUnit.MILLISECONDS)) {
try {
} finally {
lock.unlock();
}
}
} catch (InterruptedException e) {
e.printStackTrace();
}
判断该锁是否被占用
lock.isLocked()
方法是判断锁是否被占用,如果被占用返回 true
,没有被占用返回 false
ReentrantLock lock = new ReentrantLock();
// 判断锁是否被占用
if (lock.isLocked()) {
// 已被占用
} else {
// 未被占用
}