公平锁禁止插队,非公平锁允许在锁空闲时抢先获取。ReentrantLock(true) 为公平锁,线程必须按AQS队列顺序获取锁,避免饥饿但吞吐较低;默认ReentrantLock()和synchronized为非公平锁,尝试CAS抢锁成功则直接占用,仅在锁释放瞬间可“插队”,并非任意跳过队列。synchronized无公平选项,基于ObjectMonitor实现,notify不保证顺序,新竞争者与唤醒线程公平竞争。ReentrantReadWriteLock默认非公平,写线程可在读队列未获取时抢先,启用公平模式后统一FIFO排队。插队是性能与公平的权衡,合理选型比关注能否插队更重要。

Java中锁的“插队”行为,本质上取决于锁的公平性策略和底层实现机制,而不是锁类型本身决定能否插队。公平锁禁止插队,非公平锁允许插队——这是最核心的区分点。
以 ReentrantLock(true) 创建的公平锁为例,线程获取锁时会先检查同步队列(AQS CLH队列)中是否有前置等待者。如果有,当前线程必须入队排队,不能尝试直接抢占。
默认的 ReentrantLock() 和 synchronized 都是非公平的。它们在 acquire 流程中会先尝试 CAS 抢锁(tryAcquire),成功就直接占用,无需排队。
JVM 对 synchronized 的实现(如偏向锁→轻量级锁→重量级锁)始终采用非公平策略。进入重量级锁后,虽然会用 ObjectMonitor 管理等待队列(_WaitSet),但 notify/notifyAll 唤醒不保证顺序,且新竞争线程可与刚被唤醒的线程再次竞争锁。
立即学习“Java免费学习笔记(深入)”;
ReentrantReadWriteLock 默认也是非公平的。它的插队规则更精细:
基本上就这些。插队不是 bug,而是权衡响应速度与公平性的设计选择。用对场景,比纠结“能不能插”更重要。
以上就是java不同锁模式下的插队探究的详细内容,更多请关注php中文网其它相关文章!
java怎么学习?java怎么入门?java在哪学?java怎么学才快?不用担心,这里为大家提供了java速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号