我何时应该使用 Marshal.FinalReleaseComObject
与 Marshal.ReleaseComObject
?
使用 Marshal.FinalReleaseComObject
会有任何危险吗?
我何时应该使用 Marshal.FinalReleaseComObject
与 Marshal.ReleaseComObject
?
使用 Marshal.FinalReleaseComObject
会有任何危险吗?
FinalReleaseComObject
有其优点,它能够更快地使程序崩溃。“COM对象已分离其基础运行时可调用包装(RCW), 不能再使用”是CLR告诉您自己处理COM引用计数而不是交给CLR处理是一个错误的提示。您可能会遇到各种问题,您不能仅仅依靠在开发机器上运行成功来验证代码是否正确。请确保在将代码部署到客户机器上时实现良好的错误报告。
该方法的优点是只有一个地方的代码有错,那就是FinalReleaseComObject
调用。如果使用ReleaseComObject
,情况会变得模糊不清得多。因为这种错误会被忽略一段时间,直到CLR调用最终的IUnknown::Release()
并销毁对象时才导致程序崩溃,距离错误的ReleaseComObject
调用非常远。但这是末日场景,更有可能的结果是该调用根本没有任何影响,因为您可能会错过难以发现的操作,例如mumble["foo"]
,这是一个很难被察觉到的索引器引用。
我的建议很明显:不要这样做。您正在与一个永远不会犯错的机器竞争,只是它执行起来略慢一些。这里有一个非常好的“现实报告”,可以在此处找到。“悄无声息的刺客”部分最为相关。
如果有必要让COM服务器立即退出,那么让计算机处理将所有引用计数归零的操作。使用GC.Collect()方法即可。但请记住,如果您想在调试时也能起作用,必须正确地调用该方法。在使用COM对象的同一方法中使用它是行不通的,详情见此答案。请将其放置在调用方法中。