关于java:后端面经JavaSynchronize和ReentrantLock区别

25次阅读

共计 1449 个字符,预计需要花费 4 分钟才能阅读完成。

1. 概念介绍

1.1 线程平安锁

Synchronize(同步锁)和 ReentrantLock(可重入锁)都是 Java 中的罕用锁,都是用来保障线程平安的。
两者都是同步锁,且都是阻塞同步。

  • 阻塞同步:当一个线程获取锁后,其余线程只能期待(进入阻塞态),期待获取锁的线程开释锁后,其余线程能力获取锁。

    1.2 偏心锁

    在多个线程申请资源的时候,如果依据线程申请的程序来分配资源,那么这个锁就是 偏心锁,反之就是非偏心锁。

    1.3 响应中断 / 期待可中断

    在线程阻塞期间,阻塞线程期待资源的应用,如果这种期待状态可能被中断,从而开释线程去做其余的事件,这就称为 期待可中断

    2. 区别

    2.1 底层实现

    Synchronize 是 Java 的关键字,ReentrantLock 是 Java 类。因而,Synchronize 是 JVM 层面语法层面的同步锁,ReentrantLock 是 API 层面的同步锁

    2.2 锁的用法

  • 设置锁和开释锁:Synchroinze 是主动加锁和开释锁的,ReentrantLock 设置和开释都须要手动操作;
  • 润饰的对象:Synchroinze 能够润饰办法和代码块,ReentrantLock 只能润饰代码块

如下代码展现了它们的具体用法:

  • Synchronize 作为关键字润饰办法或者代码块即可;

    //synchronized 润饰一个办法时,这个办法叫同步办法。public synchronized void test() {// 办法体 ``}
    synchronized(Object){
    // 括号中示意须要锁的对象.
    // 线程执行的时候会对 Object 上锁
    }
  • ReentrantLock 的应用须要先创立锁对象,而后在须要加锁的代码块中调用 lock()办法加锁,应用结束后调用 unlock()办法开释锁。

    public class LockExample {
      // 创立锁对象
      private final ReentrantLock lock = new ReentrantLock();
      public void method() {
          // 加锁操作
          lock.lock();
          try {// ...} finally {
              // 开释锁
              lock.unlock();}
      }
    }

2.3 锁的特点

ReentrantLock 相比于 Synchronize,有以下特点:

  • 响应中断:ReentrantLock 能够响应中断,也就是在其余线程阻塞期间,能够在长时间无奈获取响应的状况下,自行中断期待状态
  • 偏心锁:ReentrantLock 默认是不偏心锁,然而能够设置为偏心锁,也就是能够依据线程申请的程序来分配资源
  • 绑定多个条件:一个 ReentrantLock 能够同时绑定多个条件,而一个 Synchronize 锁只能绑定一个条件。

这些特点都是 Synchronize 锁所不具备的。

2.4 性能比拟

Sychronize 是 JVM 层面的同步锁,实现简略,性能较好;
ReentrantLock 是 API 层面的同步锁,须要手动创立和开释锁,性能较差,然而减少了很多特点,灵活性较好。

2.5 实用场景

Synchronize 实用于:

  • 简略的同步场景;
  • 对同步性能有较高要求
  • 不须要响应中断、偏心锁、绑定多个条件;

ReentrantLock 实用于:

  • 需要更简单的同步场景
  • 对性能要求较低
  • 须要响应中断、偏心锁、绑定多个条件;

3. 总结比拟

对上述内容进行总结,如下表所示:

参考文献

  1. Synchronize 和 ReentrantLock 区别
  2. 面试突击:synchronized 和 ReentrantLock 有什么区别?
  3. Java 中 synchronized 和 ReentrantLock 的区别

正文完
 0