所以我很好奇,在 .NET 中的实例 x
上,GC(尤其是终结)会发生在什么时候:
x
没有被任何东西引用x
有一个静态的DbConnection
属性y
是与x
相同的类的实例
y
仍然被某些东西引用
令我震惊的是,在这种情况下,x
可能会被外部引用声明为已死 - 但对其执行终结可能会导致 DbConnection
在 时被释放y
仍然需要并持有对它的引用。
那么,在我描述的场景中,x
是被收集的吗?它最终确定了吗?还是在收集其中任何一个之前,它类型的所有实例都需要在堆中成为孤儿?是否会在每个实例中完成?
我想是的,是否要遵循一般规则:永远不要在终结器中触摸静态或其他共享对象?
最佳答案
是的,x
实例符合 GC 条件。 DbConnection
,因为它是静态的,所以在这种情况下与实例完全无关,并且与确定对象是否符合 GC 条件无关。只要静态属性持有引用,它就不会被收集。
Never touch a static or otherwise shared object in your finalizers?
这通常是一个很好的决定。通常,永远不要为托管类型编写终结器,除非它们正在包装非托管资源,此时该类型除了管理该资源外什么都不做(理想情况下)。即便如此,尽可能使用 SafeHandle
通常是更好的方法。
关于c# - 具有静态成员的未引用对象的 .NET GC,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25536252/