我正在尝试使用.NET 4编写单元测试,以确保在运行某些代码后可以对对象进行垃圾回收。在Java中,我会使用assertGC来确保收集弱引用。我怎样才能为.NET编写这种类型的测试?
我尝试将WeakReference
保留到对象并调用GC.Collect()
,但正如您所期望的那样,有时会收集我的对象,有时则不会。请注意,这是用于单元测试,而不是生产代码。我不希望GC.Collect()在我真实的代码库中。
我正在使用C#,但同样的答案对VB.NET也有好处。
答案 0 :(得分:1)
试试这个:
运行5分钟,仍然没有例外......你确定你的代码没有在某个地方引用你的对象吗?
using System;
internal class Program
{
private static void Main(string[] args)
{
int cnt = 0;
while (true)
{
++cnt;
bool gced = false;
Action handler = () => gced = true;
new Foo(handler);
GC.Collect();
GC.WaitForPendingFinalizers();
Console.Out.WriteLine("{0} : {1}", cnt, gced);
if (!gced)
{
throw new Exception("WTF?");
}
}
}
}
class Foo
{
private readonly Action _onFinalized;
public Foo(Action finalized)
{
_onFinalized = finalized;
}
~Foo()
{
if (_onFinalized != null) _onFinalized();
}
}
答案 1 :(得分:0)
看起来这在.NET 4中是不可能的。虽然可以知道对象是否不能被垃圾收集(例如有一个对它的引用),但是没有办法确定地知道是否对象可以被垃圾收集。
使用WeakReference或finaliser(并调用GC.Collect())可能收集对象,但除非它在第0代,否则它很可能不会。
参考文献: