自旋锁是什么
自旋锁(Spin Lock) 是一种轻量级的同步机制,线程在尝试获取锁失败时,不立即阻塞,而是通过忙等待(循环检查锁状态)直到锁可用。它适用于锁持有时间短、竞争不激烈的场景,能减少线程切换开销。
关键事实
- 基本原理:
- 线程通过循环(“自旋”)检查锁是否释放,而不是进入阻塞状态。
- 通常用原子操作(如 CAS,Compare-And-Swap)实现。
- 实现方式:
- 原子变量:如 Java 的 AtomicBoolean,通过 CAS 更新锁状态。
- 循环检查:线程不断尝试获取锁,直到成功。
- 特点:
- 忙等待:线程保持运行,占用 CPU。
- 短时高效:锁释放快时,避免上下文切换(约 10-100 微秒)。
- 典型场景:
- 多核 CPU:一个核心自旋,其他核心处理任务。
- 短暂临界区:如内存操作、简单计数器。
延伸与面试角度
- 与互斥锁对比:
- 自旋锁:忙等待,适合短时间锁,CPU 占用高。
- 互斥锁(Mutex):阻塞等待,适合长时间锁,节省 CPU。
- 为什么高效?:
- 避免线程切换(创建、挂起、唤醒的开销)。
- 多核环境下,一个线程自旋不影响其他核心。
- 适用场景:
- 高并发短操作:如 Redis 单线程模型外的 I/O 线程同步。
- 操作系统内核:短暂资源访问。
- 优缺点:
- 优点:低延迟,适合微秒级锁。
- 缺点:长时自旋浪费 CPU,可能导致死循环。
- 优化:
- 自适应自旋:如 Java ReentrantLock,动态调整自旋次数。
- 限次自旋:超过阈值(如 10 次)后阻塞。