scala 的 `synchronized` 并非关键字,而是 `anyref` 类定义的普通方法,支持点号调用、中缀调用和作用于 `this` 的隐式调用,三者语义一致但锁对象不同——关键在于调用主体(即锁实例)的选择。
在 Scala 中,synchronized 是 AnyRef(即 Java Object 的别名)上的一个实例方法,其签名等价于:
final def synchronized[T](body: => T): T
这意味着它必须被某个对象调用,而该对象本身即为同步所依赖的监视器锁(monitor lock)。因此,所谓“不同用法”,本质是调用主体不同,而非语法糖差异。下面逐一解析常见写法:
✅ 1. 隐式锁:synchronized { … }(等价于 this.synchronized { … })
这是最简写法,省略了调用者,默认以当前对象(this)为锁:
class Counter {
private var count = 0
def increment(): Unit = synchronized { count += 1 } // 锁住 this
}
⚠️ 注意:若多个线程操作同一个实例,此方式有效;但若并发访问不同实例,则互不阻塞——因为锁对象不同。
✅ 2. 显式对象锁:lock.synchronized { … }(推荐)
显式创建专用锁对象,避免污染业务对象语义,提升可读性与安全性: