C# 最整洁的方式';重置';.NET应用程序中的所有静态变量

C# 最整洁的方式';重置';.NET应用程序中的所有静态变量,c#,asp.net,static-members,C#,Asp.net,Static Members,撇开可怕不谈,如果我有一个.NETWebApp,它的静态变量分散在多个类中,那么什么是最简单的方法来“清除”它们,使其全部返回null 在我的脑海中,使用 System.Web.HttpRuntime.UnloadAppDomain() 问题背后的原因: 我们正在缓存一些非常大的字典集合,这些集合的创建成本很高,有时需要重置。卸载听起来是最简单的方法,但您不希望经常这样做;坦率地说,我会非常怀疑任何例行要求这样做 如果您想在不卸载的情况下完成这项工作,您必须逐个案例来了解其含义。特别是,强制

撇开可怕不谈,如果我有一个.NETWebApp,它的静态变量分散在多个类中,那么什么是最简单的方法来“清除”它们,使其全部返回null

在我的脑海中,使用

System.Web.HttpRuntime.UnloadAppDomain() 
问题背后的原因:
我们正在缓存一些非常大的字典集合,这些集合的创建成本很高,有时需要重置。

卸载听起来是最简单的方法,但您不希望经常这样做;坦率地说,我会非常怀疑任何例行要求这样做

如果您想在不卸载的情况下完成这项工作,您必须逐个案例来了解其含义。特别是,强制将静态构造函数/类型初始值设定项/静态字段初始值设定项设置为值的值设置为null可能会彻底破坏应用程序


请注意,静态变量很少适用于web应用程序,但缓存除外(然后必须小心管理)

如果您真的有这样的数据,而不是多个静态变量,那么您可以将state类上的实例变量视为一个伪单例,这样每个数据集群只有一个swap引用

值得考虑的是,在某个地方有一个事件,静态代码在初始化自己时只能订阅一次,然后在需要时触发该事件,即

myStaticData = new SomeExpensiveThreadSafeCacheDictionary();
GlobalKillSwitch.ResetCache += delegate { myStaticData.Clear(); };
我用这个

    public static void ResetAllStaticsVariables(Type type)
    {
        var fields = type.GetFields(BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.FlattenHierarchy | BindingFlags.Public);
        foreach (var fieldInfo in fields)
        {
            fieldInfo.SetValue(null, GetDefault(type));
        }
    }

    public static object GetDefault(Type type)
    {
        if (type.IsValueType)
        {
            return Activator.CreateInstance(type);
        }

        return null;
    }

你能给出更多想要这样做的原因吗,以及不使用静态变量来启动一个带有静态变量的web应用程序是否可行??听起来很冒险,不太适合负载平衡。可能是整个程序集的递归反射?“静态变量很少适用于web应用程序”这一点不会出错——为什么?我不是在质疑你是否正确,我真的很想知道为什么——似乎找不到关于谷歌的任何进一步信息。@SkonJeet,因为web应用程序正在处理许多请求;请求中使用的大多数数据都是特定于该请求的,您不希望它靠近可能影响其他请求的静态字段。当使用静态字段时,需要考虑线程安全性(多个竞争无关的请求,以及在流水线期间不同线程之间的单个请求跳转)。别误会我的意思:他们有用处。。。但是:有很多caveats@SkonJeet另外,ASP.NET通常指IIS。IIS随意回收工作进程,回收时静态变量被装箱。根据它的用途,不断地重新初始化它可能是一个问题。@AdamHouldsworth它只会根据需要重新初始化,因此不会比根据上下文重新初始化更频繁。@maxp这就是为什么我说取决于它的用途。如果您错误地使用它来缓存某些内容,那么这将意味着您的缓存执行的抓取次数超过了需要的次数。我在尝试在集成测试运行之间重置桌面应用程序的状态时发现了这个答案,这对它真的很有好处。