
🔵2025年Java面试宝典免费领:
链接: https://pan.baidu.com/s/1RUVf75gmDVsg8MQp4yRChg?pwd=9b3g
提取码: 9b3g
一、synchronized的底层实现原理
作为Java开发者最熟悉的同步机制,synchronized底层其实是通过对象头的Mark Word实现的。当线程进入同步代码块时,JVM会自动给对象加锁,这个锁在JDK1.6之后会根据竞争情况从偏向锁升级到轻量级锁,最后升级为重量级锁。
每个Java对象都关联着一个Monitor(监视器),底层通过**操作系统互斥量(Mutex Lock)**实现线程阻塞。当发生锁竞争时,未获得锁的线程会被挂起进入等待队列,这种机制保证了原子性但会带来线程上下文切换的开销。
二、Lock接口的实现特点
与synchronized不同,Lock是一个显式锁接口(如ReentrantLock),它基于AQS(AbstractQueuedSynchronizer)框架实现。AQS内部维护了一个双向链表结构的等待队列,通过CAS操作控制线程的排队和唤醒。
Lock最核心的特性在于灵活性:
- 支持非阻塞获取锁(tryLock)
- 可中断等待(lockInterruptibly)
- 支持公平锁与非公平锁策略
- 提供Condition实现精准的条件唤醒
三、synchronized和Lock的核心区别
1. 实现层级不同
synchronized是JVM层面的内置锁,而Lock是JDK层面的API。这意味着synchronized的优化(如锁消除、锁粗化)由编译器自动完成,而Lock需要开发者手动控制锁的获取和释放。
2. 锁的可见性保障
synchronized遵循JMM规范的happens-before原则,能自动保证共享变量可见性。而使用Lock时,必须结合volatile变量或Atomic类来保证内存可见性。
3. 异常处理机制
synchronized在代码块执行完毕或抛出异常时会自动释放锁,而Lock必须写在finally块中手动释放,否则可能导致死锁。
四、如何选择同步工具
在高并发且需要精细控制锁的场景下(如限流、熔断),Lock是更好的选择。而synchronized适合简单的临界区保护,比如单例模式的双重检查锁。

五、面试高频问题解析
1. synchronized锁升级过程
- 初始状态:无锁
- 首次线程访问:升级为偏向锁(Mark Word记录线程ID)
- 多个线程轻度竞争:升级为轻量级锁(CAS自旋)
- 重度竞争:膨胀为重量级锁(OS互斥量)
2. AQS如何实现可重入性
ReentrantLock通过内部Sync类维护了一个计数器(state变量),每次重入时state+1,释放锁时state-1,直到state=0才完全释放锁。
六、避坑指南
- 避免在synchronized代码块中调用外部方法(可能引发死锁)
- Lock.unlock()必须放在finally块中
- 读写场景优先考虑ReadWriteLock而非synchronized

🔥面试鸭返利网小贴士:准备面试的同学可以到面试鸭返利网购买会员,通过本站下单可返利25元,用更低的成本获取最新的面试题库。技术学习要精打细算,省下来的钱买杯咖啡继续撸代码不香吗?


