处理存储在公共静态字段中的IDisposable对象

时间:2012-12-25 18:14:57

标签: c# .net idisposable

如果一个类有一个实现IDisposable的实例字段,那么包含的类实现了IDisposable和类,它在Dispose方法中对Dispose方法进行了记录。

public class A : IDisposable 
{
    public System.Drawing.Font font = new Font("Arial", 10.0f);

    public void Dispose()
    {
        font.Dispose()
    }
}

(我知道我没有正确处理配置模式,但是样本代码应该足够好了)

如果字段是静态字段,那么调用字段的Dispose应该在哪里?

public class B
{
    public static System.Drawing.Font font = new Font("Arial", 10.0f);
}

我可以让B类实现IDisposable并且调用font.Dispose但是如果稍后再使用B.font会导致问题。除了你必须记住访问静态方法的dispise,你需要创建一个实例来调用Dispose。

我也可以创建一个静态的Dispose方法,但是用户必须记住调用Dispose并且必须确保它们是程序中它的最后一个用户。

4 个答案:

答案 0 :(得分:8)

加载类型时会初始化静态字段。

因此,从逻辑上讲,在卸载包含类型时配置分配给静态字段的对象是有意义的。

但是,类型不会被卸载。 AppDomains周围可能存在一些奇特的复杂问题,但我怀疑这不适用于您的情况。

因此我不会处置该实例,否则您将拥有一个公开可用的不适合使用的对象实例。

答案 1 :(得分:3)

如果该字段是静态的,那么可能的目的是让它在应用程序的整个持续时间内持续吗?因为它只需要在应用程序关闭时处理掉。这将以某种方式发生,单独发生 -

如果您计划在应用程序的生命周期内多次将静态字段重新分配给不同的IDisposable对象,那么当然您需要在重新分配时处置旧对象。也许你可以使用一个属性?并不是说我已经考虑了很多,而是像:

// private - don't write to this field from outside the property setter
static Font font = new Font("Arial", 10.0f));

public static Font Font
{
  get
  {
    return font;
  }
  set
  {
    var oldFont = font;
    if (oldFont != null)
      oldFont.Dispose();
    font = value;
  }
}

答案 2 :(得分:2)

您可以像处理任何其他物体一样处理它。它没有任何区别。静态对象只是每个类可用的对象。它仍然是一个事实的例子。当然,您可能不希望这样做,因为在您处理它之后,某人仍然可以访问它并获得ObjectDisposedException例外。

    static void Main(string[] args)
    {
        using (Test.Instance)
        {

        }  

        Thread.Sleep(TimeSpan.FromSeconds(10));
    }

    public class Test:IDisposable
    {
        public static Test Instance = new Test();
        public void Dispose()
        {
            Console.WriteLine("Disposed");
        }
    }

输出是:

  

弃置

根据您更新的示例:

public class A
{
    public static System.Drawing.Font font = new Font("Arial", 10.0f));
}

您可以A.font.Dispose()using(A.font)

总的来说,我认为这个想法是你真的不会有一个公共的静态一次性场,因为通过使它静止你意味着它应该在应用程序的生命周期中存在。如果它必须是一次性的,你应该使它变得懒惰并使其可以线程安全地重新初始化,否则在处理后访问它将抛出异常。或者您可以在应用程序结束代码中使用挂钩并安全地处理所有静态一次性用品。您也可以在某处开始注册您的一次性用品。只是一个想法

答案 3 :(得分:-1)

您不能处置静态类,因为它没有实例