我尝试了一个简单的实验来验证垃圾收集器的功能。关于3.9 Automatic memory management中的自动内存管理,请引用.NET(MSDN)。对我来说,这听起来像是C++中的共享指针。如果对象的引用计数器变为零,则垃圾回收器将对其进行释放。
因此,我尝试在主窗体内创建一个函数。该函数在我的主窗体的Shown事件函数内部调用,该函数在构造函数之后执行。这是实验代码。

    public void experiment()
    {
        int[] a = new int[100000];
        int[] b = new int[100000];
        int[] c = new int[100000];
        int[] d = new int[100000];

        a = null;
        b = null;
        c = null;
        d = null;
    }
结果如下:
分配内存之前

分配内存后

离开功能范围之前

离开功能范围后

为什么即使将垃圾回收器设置为null,也不能取消分配数组a,b,c,d分配的内存?

最佳答案

.NET垃圾收集器是高度优化,复杂的软件。它经过优化,可以使您的程序尽可能快地运行,并且不会占用太多内存。

由于释放内存的过程需要一些时间,因此垃圾收集器通常会等待运行它,直到您的程序使用了大量的内存为止。然后,它会立即完成所有工作,这会导致在相对较长的时间后您的程序出现较小的延迟(而不是之前的许多较小的延迟,这会使您的程序变慢)。

所有这些意味着,垃圾收集器运行的时间是而不是可预测的

您可能会多次调用测试(循环中有一些Sleep()),然后观察内存使用情况是否逐渐增加。当程序开始占用大量可用物理内存时,其内存使用量将突然降至接近零。

有几个函数(例如GC.Collect())强制执行多个级别的垃圾收集,但强烈建议除非您知道自己在做什么,否则不要使用,因为这会使您的软件变慢并停止垃圾回收器。以最佳方式进行工作。

10-08 13:44