当前位置:  开发笔记 > 编程语言 > 正文

进程被终止时,C#清理非托管资源

如何解决《进程被终止时,C#清理非托管资源》经验,为你挑选了2个好方法。

我有一个类来实例化一个COM exe进程.这堂课是

public class MyComObject:IDisposable
{
    private bool disposed = false;
    MyMath test;

    public MyComObject()
    {
        test = new MyMath();
    }

    ~MyComObject()
    {
        Dispose(false);
    }

    public double GetRandomID()
    {
        if (test != null)
            return test.RandomID();
        else
            return -1;
    }

    public void Dispose()
    {
        Dispose(true);

        GC.SuppressFinalize(this);
    }

    private void Dispose(bool disposing)
    {
       if (test != null)
       {
           Marshal.ReleaseComObject(test);
           test = null;
       }

       disposed = true;
    }
}

我把它称之为如下

static void Main(string[] args)
    {
        MyComObject test = new MyComObject();
        MyComObject test2 = new MyComObject();

        //Do stuff

        test.Dispose();
        test2.Dispose();

        Console.ReadLine();
    }

现在,这会在程序正常执行时清理我的COM对象.但是,如果我在执行过程中关闭程序,框架就不会调用释放我的非托管对象的代码.这是公平的.但是,有没有办法迫使程序自行清理,即使它被杀死了?

编辑:从任务管理员的硬杀,它看起来并不乐观:(



1> Mark Bracket..:

在最后尝试或使用子句包装它将使你在那里的大部分方式:

using (MyComObject test = new MyComObject())
using (MyComObject test2 = new MyComObject()) {
    // do stuff
}
Console.ReadLine();

但是,关闭应用程序的具体细节将决定您可以执行的任何其他措施(例如使用CriticalFinalizerObject).

认为关闭的控制台应用程序(从小x开始)与Ctrl-C相同 - 在这种情况下,您可以订阅Console.CancelKeyPress.

编辑:您还应该使用ReleaseComObject,直到它返回<= 0.



2> Jon Skeet..:

嗯,最好的做法是使用using语句:

using (MyComObject test = new MyComObject())
using (MyComObject test2 = new MyComObject())
{
    //Do stuff
}

这实际上是finally在块的末尾自动调用块来调用dispose.你应该有using语句几乎只要你有你承担清理责任IDisposable的实例.但是,它并不能解决您的整个过程突然中止的情况.这是非常罕见的,你可能不想担心它.(这很难绕过它.)我已经预料到你的终结器会被你以前的代码调用,但是...

推荐阅读
重庆制造漫画社
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有