会员专享
请先
登录,登录后可使用今日免费解锁;
开通会员后可解锁完整内容。
解题思路
这题是双重检查锁的懒加载单例。配置表放在唯一的那份实例上,实例引用本身是类的静态状态。
引用必须是静态的。它记录的是这一份对象在哪里,属于类,不属于某一个已经造出来的对象。构造完成后,后面的调用都顺着同一个静态引用找到它。配置表和出生编号描述的是这份实例,所以是对象成员。
获取实例时做两次判断。外层判断看见引用已经发布,就直接返回,发布之后的调用不必再抢锁。几个调用方可能都在外层看见了空引用,然后排队抢同一把锁。抢到锁之后还要再判断一次,只有仍然为空的那一个执行构造。
发布引用时要让其他调用方看见构造已经完成。Java 里对象的分配、引用写入和构造函数可能重排,所以静态引用用 volatile。C++ 用原子指针,构造完成后以 release 写入,读取时用 acquire。Python 没有 volatile,互斥锁的获取和释放自带可见性,因此要在持锁期间把构造完的对象赋给类变量。