如何使现有Java类/接口实现成为单例?

时间:2012-06-12 17:25:30

标签: java spring singleton

假设我在Spring中使用ApplicationContext实现。

ApplicationContext是Java Spring Framework中的一个接口,我无法改变它。

如何确保此实现只能有一个实例?

例如。我有以下代码 -

public class ApplicationContextSingleton 
{
     private static ApplicationContext context;
     private static int numberOfInstances = 0;

     public static ApplicationContext getApplicationContext()
     {
         if(numberOfInstances == 0)
         {
             context = new ClassPathXmlApplicationContext("spring.xml");
             numberOfInstances++;
         }
         return context;
     }
}

这样,我可以确保只有一个ApplicationContext实例,只要它获得如下 -

ApplicationContext context = ApplicationContextSingleton.getApplicationContext();

但这并不能阻止另一位程序员说 -

ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml"); 

从而创建一个新的ApplicationContext。如何防止这种情况发生?

5 个答案:

答案 0 :(得分:3)

你想让ApplicationContext成为一个单身,所以我用我自己的自定义类覆盖该类,确保它首先出现在类路径上,并使它具有私有构造函数。

也就是说,如果你已经死定了它就成了一个单身人士。正如其他答案和评论所指出的,有更好的方法可以解决您的问题。

应该注意,覆盖多个库通常是一个坏主意,因为它可能是后来头痛的原因,尤其是当您尝试升级框架版本时。

答案 1 :(得分:2)

除非有人能提出具有创造性的东西,否则我认为没有办法做到这一点。这类似于尝试使int成为单身人士。只是不会发生,因为你没有任何控制你没有写的类的使用。您只需要相信您的开发人员不要创建第二个上下文。

或者,我几乎可以保证这将是不可能的,但是 可以 获取spring的完整源代码,进行一些代码更改以创建上下文单身人士,然后自己建立。不是一个可能的解决方案,但无论如何我觉得有必要指出它。

答案 2 :(得分:1)

没有办法,因为

Spring没有将ClassPathXmlApplicationContext实现为Singleton模式。 通知每个人你有一个实用工具方法来访问上下文对象,并使用new创建上下文是昂贵的。

答案 3 :(得分:1)

  1. 使用自动构建系统,只要将代码提交到软件存储库,就会构建代码。
  2. 将工具集成到构建过程中,如FindBugs或PMD。如果这些工具触发某些条件,则构建失败并且不允许生成任何工件。
  3. 在您的集成工具中创建一个案例,寻找开发人员创建自己的上下文。
  4. 所以你无法阻止他们这样做,但你可以阻止他们将这些东西推到你的开发,qa和prod环境中。这可能看起来有点矫枉过正,但这种过程将有助于您的开发人员可以做但不应该做的数百件事。

答案 4 :(得分:0)

Josh Block建议在Effective Java中使用枚举。 This isnt a link to that book,但它显示了他和更老的(替代)方式