【问题标题】:A good way to implement Singleton pattern with Spring用 Spring 实现单例模式的好方法
【发布时间】:2016-07-12 11:57:26
【问题描述】:

我想在 Spring 应用程序的上下文中实现单例模式。 所以即使是我的单例对象也会被spring创建。

要做到这一点:

我放了一个实现ApplicationContextAware的类来从spring上下文中获取bean:

public class AppContext implements ApplicationContextAware
{

  /**
   * Private instance of the AppContext.
   */
  private static AppContext _instance;

  /**
   * @return the instance of AppContext
   */
  public static AppContext getInstance()
  {

    return AppContext._instance;
  }

  /**
   * Instance of the ApplicationContext.
   */
  private ApplicationContext _applicationContext;

  /**
   * Constructor (should never be call from the code).
   */
  public AppContext()
  {
    if (AppContext._instance != null)
    {
      throw (new java.lang.RuntimeException(Messages.getString("AppContext.singleton_already_exists_msg"))); //$NON-NLS-1$
    }
    AppContext._instance = this;
  }

  /**
   * Get an instance of a class define in the ApplicationContext.
   * 
   * @param name_p
   *          the Bean's identifier in the ApplicationContext
   * @param <T>
   *          the type of the returned bean
   * @return An instance of the class
   */
  @SuppressWarnings("unchecked")
  public <T> T getBean(String name_p)
  {

    return (T) _applicationContext.getBean(name_p);
  }

  @Override
  public void setApplicationContext(ApplicationContext applicationContext_p) throws BeansException
  {
    _applicationContext = applicationContext_p;
  }
}

我的单身班:

    public class MySingleton {

    private static MySingleton instance= null; 
    public static final String BEAN_ID = "mySingletonInstanceId"; 

    private MySingleton(){}


    public static MySingleton getInstance(){
       return AppContext.getInstance().getBean(mySingletonInstanceId.BEAN_ID);
    }
   }

我的 application.xml 文件:

    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:jaxws="http://cxf.apache.org/jaxws"
           xmlns:cxf="http://cxf.apache.org/core" xmlns:jaxrs="http://cxf.apache.org/jaxrs"
           xsi:schemaLocation="
    http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd
    http://cxf.apache.org/jaxws http://cxf.apache.org/schemas/jaxws.xsd
    http://cxf.apache.org/jaxrs
    http://cxf.apache.org/schemas/jaxrs.xsd
    http://cxf.apache.org/core http://cxf.apache.org/schemas/core.xsd">

    <!--some code-->

        <bean id="idAppContext" class="com.AppContext" />
        <bean id="mySingletonInstanceId" class="com.MySingleton"/>

    <!--some code-->

    </beans>

你觉得我的代码好吗?

instance 字段不再需要?

考虑到 Spring 将管理一切,getInstance() 只需返回由 spring 创建的单例实例?

【问题讨论】:

  • 不要编写执行此操作的代码。使用依赖注入代替这个丑陋的装置。
  • 默认情况下,spring bean 是单例的。尝试使用依赖注入,spring 会为你做这件事。
  • 如果我理解的话,Spring应用程序中不再需要使用单例模式了吗?

标签: java spring design-patterns singleton


【解决方案1】:

我得出了与您相同的结论和类似的实现。如果有人需要单例模式,那么这就是使用 Spring 的方法。我希望我早点看到这篇文章。

有些人不明白 Singleton Pattern 与 Spring 定义的 Singleton 不同,这里解释:Singleton design pattern vs Singleton beans in Spring container

绕过 Spring 使用的反射是很棘手的,它有效地忽略了私有访问修饰符。

话虽如此,有些人讨厌单例模式,从这篇文章可以看出:http://puredanger.github.io/tech.puredanger.com/2007/07/03/pattern-hate-singleton/

这导致我重新考虑使用单例模式设计,而是改用 Spring 单例。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-24
    • 2017-02-25
    相关资源
    最近更新 更多