【发布时间】:2011-12-18 10:16:02
【问题描述】:
背景/问题:
我对单例设计模式还很陌生。我曾在 Web 应用程序中使用过它(在 SO 社区的帮助下):
public static AppGlobal Instance
{
get
{
if (HttpContext.Current.Session != null)
{
HttpSessionState session = HttpContext.Current.Session;
if (session["AppGlobalInstance"] == null)
{
session["AppGlobalInstance"] = new AppGlobal();
}
return (AppGlobal)session["AppGlobalInstance"];
}
else
{
return null;
}
}
}
上面的实现对我来说很有意义,因为AppGlobal 的实例存储在会话中。当会话终止时,AppGlobal 终止。如果我在 Web 应用程序调用的类库 中使用相同的设计模式会发生什么?例如,用户请求一个页面,该页面调用不知道会话的 DLL 中的方法。存储在单例实例中的数据是否会通过多次调用进行持久化?
private static readonly Singleton instance = new Singleton();
private Singleton() { }
public static Singleton Instance
{
get
{
return instance;
}
}
其他信息:
这就是我想要完成的事情:我有一个 Web 应用程序,它将接收来自第三方应用程序的 XML 请求。此 XML 将告诉我的 Web 应用程序执行三件事之一(或全部三件事)。我想要一个类的单例实例,它存储可以被多个类访问的数据。我希望单例实例在每次请求后 DIE 。如果上述方法不能实现这一点,那么实现它的最佳方法是什么?
注意:此 Web 应用程序在单个服务器上运行,并且永远不会在场中运行。
编辑 1:
根据下面的建议,我使用System.Web.HttpContext.Current.Session 来存储我的类实例。对于每个会话都是唯一的单例,这看起来是正确的方法吗(记住我在类库中)?
public static Ariba Instance
{
get
{
if (HttpContext.Current.Session != null)
{
HttpSessionState session = HttpContext.Current.Session;
if (session["AribaInstance"] == null)
{
session["AribaInstance"] = new Ariba();
}
return (Ariba)session["AribaInstance"];
}
else
{
return null;
}
}
}
【问题讨论】:
-
您提到您希望单身人士在每个请求之后死亡。如果是这种情况,您不需要在会话中存储任何内容。相反,您可以将对象存储在 HttpContext.Current.Items["AribaInstance"] 中。我要补充一点,如果您确实使用 HttpContext.Current,那么您将在对类库进行单元测试时遇到一些困难,因为 HttpContext.Current 不会在 ASP.NET 之外填充(Session 也是如此。)如果单元测试对您很重要,您需要包装上下文和会话对象。
-
@AndyWilson,感谢您的提醒和回答!
标签: c# design-patterns singleton