4

我有一个类,这个类的“值”变量包含从文件读取的大数据:

 public class MyClass : IDisposable
{
    public string name {get; set;}
    public string value {get; set;} //I'm load huge data for this variable

    public MyClass(string name, string value)
    {
        this.name = name;
        this.value = value;
    }

    public void Execute()
    {
        Console.WriteLine(this.name + ":" + this.value);
    }

    public void Dispose()
    {
        Dispose(true);            
        GC.SuppressFinalize(this); 
    }

    protected virtual void Dispose(bool disposing)
    {                     
        if (disposing)
        {
            this.name = null;
            this.value = null;
        }                      
    }
}

我在列表中使用这个类,它是全局变量

List<MyClass> listQ = new List<MyClass>() { new MyClass("1", "BIGDATA1"),
            new MyClass("2", "BIGDATA2"),
            new MyClass("3", "BIGDATA3"),
            new MyClass("4", "BIGDATA4"),
            new MyClass("5", "BIGDATA5"),
            new MyClass("6", "BIGDATA6"),
        };

    private void FUC_Load(object sender, EventArgs e)
    {                        
        foreach (MyClass m in listQ)
        {
            m.Execute();
            m.Dispose();
        }                       
    } 

所以我想问如果我这样做,会有什么问题吗?我的对象是否会被处置?有什么最好的方法吗?感谢!

4

4 回答 4

9

那是使用不当Dispose()

Dispose()旨在用于两种情况:

  1. 当您处置非托管资源时。
  2. 当您处理本身实现的类型的对象时IDisposable

您应该将您的Dispose()方法重命名Clear()为更好地描述正在发生的事情。

或者(我认为在你的情况下可能更好)你可以简单地将listQ引用设置为null一旦你迭代了它。由于您在迭代时破坏了它所保存的数据,因此很明显您以后不需要这些数据。

如果将listQ引用设置为 null,则它的所有内存,包括它持有引用的所有对象的内存,将(最终)被垃圾收集,假设没有其他东西持有对这些对象的引用。

请注意,您必须确保所有对 的引用listQ都设置为空。(堆栈上对它的引用将在返回声明它们的方法时自动消失,因此您无需担心这些。)

于 2013-04-28T09:06:15.963 回答
2

如果可能,请使用 Queue 类而不是 List。这样,当你出队时,你会自动从集合中删除对象:

while(queueCollection.Count > 0) {
    MyClass obj = queueCollection.Dequeue();
    obj.Execute();
}
于 2014-10-20T19:34:34.780 回答
2

我猜您真的很担心对象会占用您的内存。除非您使用非托管资源(例如访问网络或远程数据库资源),否则您不必担心。因为这不是您的情况,所以运行时足够智能以释放资源认为必要时。

.net 运行时中的垃圾收集为您管理托管资源,您不必太担心释放托管句柄。

当您的 List 引用超出范围或 GC 知道此列表未使用时,该对象将从内存中清除。

于 2013-04-28T09:10:34.010 回答
-1

IDisposable 接口用于确定性终结。

它最初是作为释放非托管资源的一种方式,但现在通常用于最终确定托管对象。

完成并不意味着释放对象。这只是您不再使用该对象的意图的表现。

如果您的对象支持打开/关闭,则应该意味着您可以多次打开和关闭它。在这种情况下,Dispose 应该调用 Close(或执行相同操作),但该对象不再可用。

IDisposable 的许多实现具有额外的逻辑来控制对象是否已被释放以及对象被释放时的事件。此事件通常用于从已添加对象的集合中删除对象。

对象本身只会在垃圾收集器回收它时不复存在。

于 2013-04-29T00:17:28.830 回答