大约四天以来,我一直在收集托管应用程序的性能计数器。在此期间,发生了以下垃圾收集:
- 第 0 代:133,695
- 第一代:133,413
- 第 2 代:133,254
其中一些是使用GC.Collect()
. 这四天有 323 人。
为什么我的所有(或基本上所有)收藏都是完整收藏?我猜这种情况会导致非常高的“% Time in GC”计数器(超过 70%,即使分配的字节/秒显着下降)。
根据配置文件,注意我正在运行 .NET 4.0、64 位并使用服务器 GC 可能很重要,也可能不重要。
大约四天以来,我一直在收集托管应用程序的性能计数器。在此期间,发生了以下垃圾收集:
其中一些是使用GC.Collect()
. 这四天有 323 人。
为什么我的所有(或基本上所有)收藏都是完整收藏?我猜这种情况会导致非常高的“% Time in GC”计数器(超过 70%,即使分配的字节/秒显着下降)。
根据配置文件,注意我正在运行 .NET 4.0、64 位并使用服务器 GC 可能很重要,也可能不重要。
我正在分配大量内存(有时超过 300 MB/秒)
这足以解释你所观察到的。这将在那一秒内触发大量收集,gen #0 和 gen #1 堆并没有那么大。这些代中的对象很有可能仍在使用中,因为它们刚刚被分配,所以第 0 代和第 1 代集合没有腾出足够的空间,几乎每个对象都被提升到第 2 代。GC对此有一个对策,它会自动增加代大小。但这无法满足你对记忆的强烈渴望。您可以使用 Perfmon.exe 中的 .NET 内存性能计数器来观察这一点。任何 .NET 内存分析器都可以通过更漂亮的图表为您提供洞察力。
以如此高的速率分配内存并不容易,您必须分配大量数组。这本身就可以解释,大于 85,000 字节的数组分配在大对象堆中。寻找重用这些数组的方法。几乎所有 .NET 集合类都在底层使用数组。