为什么 Spring 框架更喜欢 mutex 而不是 volatile?

Why Spring framework preferes mutex over volatile?

public abstract class AbstractApplicationContext extends DefaultResourceLoader
        implements ConfigurableApplicationContext, DisposableBean {

   private boolean active = false;
   private final Object activeMonitor = new Object();

   public boolean isActive() {
      synchronized (this.activeMonitor) {
         return this.active;
      }
   }

   protected void cancelRefresh(BeansException ex) {
       synchronized (this.activeMonitor) {
          this.active = false;
       }
   }

   ...
}

使用 mutex 而不是 volatile 来保证读取一致性有什么必要的吗,或者这只是首选项/代码约定/等的问题?乍一看,mutex 并没有带来什么新东西,除了我们有更多的代码行。此外,我们可以在同步块中更改多个变量,但这不是示例中的问题 - 只有一个变量被更改。

P.S。我知道什么是 mutex 和 volatile,请避免在答案中解释 JMM。

没有真正的原因,所以可能只是一个惯例(个人或项目的),但它们是 AtomicBooleans 版本 4.1.6。

active值是正常使用的(get/set),但是有一个closed使用了compareAndSet.

volatilesynchronized 不同。 volatile 只关心线程间数据的可读性。 syncronized 在这种情况下也会阻止并发访问。

此外 before JDK 1.5 volatile 关键字的 use/implementation 未完全或正确实现,因此更安全地使用互斥体,尤其是在 Spring 中的代码中自开始或 JDK 1.5 之前。对于需要支持 Java <= JDK 1.5.

的旧版本框架中的代码,这仍然适用

在 JDK 1.5 或更高版本可用的框架的较新部分中,您会看到更多地使用 volatileAtomic* 类。在仅支持 JDK 1.6 及更高版本的较新版本中,已完成大量清理工作。