Java高频面试之并发编程-20

发布于:2025-05-26 ⋅ 阅读:(81) ⋅ 点赞:(0)

hello啊,各位观众姥爷们!!!本baby今天又来报道了!哈哈哈哈哈嗝🐶

面试官:说说synchronized 和 ReentrantLock的区别?

synchronizedReentrantLock 是 Java 中实现线程同步的两种机制,它们的主要区别如下:


1. 实现机制

  • synchronized:是 Java 的关键字,基于 JVM 内置的监视器锁(Monitor)实现,自动加锁和释放锁。
  • ReentrantLock:是 java.util.concurrent.locks 包下的一个,基于 API 实现,依赖 lock()unlock() 方法手动控制。

2. 锁的获取与释放

  • synchronized
    自动管理锁的获取和释放,进入同步代码块时加锁,退出时(包括正常退出或抛出异常)自动释放锁。
  • ReentrantLock
    必须显式调用 lock() 加锁,并在 finally 块中调用 unlock() 释放锁,否则可能导致死锁。

3. 可中断性

  • synchronized
    线程在等待锁时不可被中断,会一直阻塞直到获取锁。
  • ReentrantLock
    支持通过 lockInterruptibly() 实现可中断的锁等待,线程在等待时可以响应中断。

4. 公平性

  • synchronized
    仅支持非公平锁(默认抢占式,不保证等待顺序)。
  • ReentrantLock
    可通过构造函数选择公平锁或非公平锁(公平锁按等待顺序分配,减少线程饥饿)。

5. 功能扩展

  • ReentrantLock 提供更灵活的功能:
    • 尝试获取锁tryLock() 可立即返回是否成功,或设置超时时间(tryLock(long timeout, TimeUnit unit))。
    • 绑定多个条件变量:通过 newCondition() 创建多个 Condition 对象,实现更细粒度的线程通信(如生产者-消费者模型)。
  • synchronized
    仅通过 wait()/notify() 实现单一条件的线程通信。

6. 性能

  • JDK 1.6 之前ReentrantLock 性能优于 synchronized
  • JDK 1.6 及之后synchronized 引入偏向锁、轻量级锁等优化,两者性能差距不大。多数场景下优先使用 synchronized(简单、稳定)。

7. 可重入性

  • 两者均为可重入锁:同一线程可重复获取同一把锁,避免死锁。

8. 异常处理

  • synchronized
    发生异常时自动释放锁,避免死锁。
  • ReentrantLock
    需在 finally 中手动释放锁,否则锁可能无法释放。

总结对比表

特性 synchronized ReentrantLock
实现方式 JVM 内置关键字 API 实现的类
锁释放 自动释放 需手动调用 unlock()
可中断性 不支持 支持(lockInterruptibly()
公平锁 仅非公平锁 可配置公平或非公平
条件变量 单一条件 支持多个条件(Condition
尝试获取锁 不支持 支持(tryLock()
性能 JDK 1.6+ 优化后接近 高竞争场景下表现更好
代码简洁性 简单,自动管理 需手动控制,更复杂

使用场景建议

  • 优先 synchronized:简单同步需求,无需复杂功能时(代码简洁、维护方便)。
  • 选择 ReentrantLock
    • 需要可中断锁、超时获取锁、公平锁等高级功能。
    • 需要细粒度的条件控制(如多个等待队列)。

技术资料大全:https://pan.q删掉汉子uark.cn/s/aa7f2473c65b

在这里插入图片描述


网站公告

今日签到

点亮在社区的每一天
去签到