代码之家  ›  专栏  ›  技术社区  ›  Kozuki

如何在生产代码中考虑单例?

  •  3
  • Kozuki  · 技术社区  · 7 年前

    我有一些java类,其中的成员变量都是 Autowired 使用Spring Bean。我认为这保证了独生子女模式。但我想知道代码是如何在生产服务器上运行的?是每个线程保证单例还是全局保证单例?我应该如何考虑开发中的并发性。

    编辑

    例如: 类接受请求并响应其收到的请求数。 在这种情况下,我们需要保证计数器的全局单态,对吗?比如说,无论我们使用多少台服务器,都应该只有一个计数器。这是隐含的保证吗?

    1 回复  |  直到 7 年前
        1
  •  6
  •   davidxxx    5 年前

    经典单例和弹簧单例的范围

    Singleton通常指在JVM上运行的整个应用程序的Singleton。
    Java经典实现就是这样,您可以自己实现它(singleton double check惯用法、enum惯用法、initialization on demand holder惯用法,等等)。
    在这些情况下,单例确实是在单例类的类加载上创建的,因此只有一次是由JVM创建的。

    春季单身人士的工作方式略有不同。
    它们确实依赖于容器。因此,如果在同一个JVM中创建多个容器,则可能会创建多个单例。现在这真的是一个角落的情况,除此之外,这些单例bean是孤立的。所以不要把重点放在它上面。


    关于并发性

    当这些是不可变的时,单例没有任何并发问题。
    当然,您可以在单例中定义依赖项和属性。 但在单例实例化之后,这些不应该改变。
    事实上,如果一个单例提供了允许更改其状态的方法,那么您一定会为处理该状态的不同线程设置竞争条件。

    因此,作为一个提示,让您的单例保持不变或尽可能保持不变。
    如果这些不能完全不变,则必须确保通过同步需要的方法/字段来处理竞争条件。