为什么需要 Lock
synchronized
不够用。
- 效率低:锁的释放情况少、试图获取锁时不能设定超时、不能中断一个正在试图获得锁的线程。
- 不够灵活:加锁和释放的时机单一,每个锁仅有单一的条件(某个对象),可能是不够的。
- 无法知道是否成功获取到锁。
Lock 用法
使用一种叫做 ReentrantLock 的具体的锁,在 finally 里释放锁。
lock 使用
lock() 方法不能被中断,一旦陷入死锁,就会陷入永久等待。
public class MustUnlock {
private static Lock lock = new ReentrantLock();
public static void main(String[] args) {
lock.lock();
try {
// 获取本锁保护的资源
System.out.println(Thread.currentThread().getName() + "开始执行任务");
} finally {
lock.unlock();
}
}
}
tryLock 使用
tryLock 获取到锁之后,需要在执行完成之后释放。官方建议的方式是使用 try 语句,解锁放在 finally 中。
public class tryLockDeadLock implements Runnable {
static Lock lock1 = new ReentrantLock();
@Override
public void run() {
try {
if (lock1.tryLock(800, TimeUnit.MILLISECONDS)) {
try {
System.out.println("线程1 获取到了锁1");
} finally {
lock1.unlock();
}
} else {
System.out.println("线程1 获取锁1失败");
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
Java 锁的分类
Java 中锁的分类乐观锁和悲观锁
乐观锁:乐观锁认为在一般情况下,一切顺利是常态,所以有事情就去做,如果出了问题再来补救。例如:原子类和并发容器等。
悲观锁:悲观锁认为,一般强狂下,资源不足,大家都来争抢是常态。如果我不锁住资源,别人就会来抢,就会造成数据的错误。 例如:synchronized 和 Lock 相关的类。
网友评论