3

我们有一个 C# 应用程序,它控制我们的一个设备并对这个设备给我们的信号做出反应。

基本上,应用程序创建线程、处理操作(访问数据库等)并与该设备通信。

在应用程序的生命周期中,它创建对象并释放它们,到目前为止,我们让垃圾收集器处理我们的内存。我读过强烈建议让 GC 在不干扰的情况下完成其工作。

现在我们面临的问题是,我们的应用程序的过程会不断增长,一步一步地增长。例子:

在此处输入图像描述

当应用程序增长时似乎有“波”,突然间,应用程序释放了一些内存,但似乎同时留下了内存泄漏。

我们正在尝试使用一些内存分析器来调查应用程序,但我们想深入了解垃圾收集器的工作原理。

你们知道另一个非常深入的 GC 文档吗?

编辑 :

这是说明应用程序行为的屏幕截图:

您可以清楚地看到我们在非常规则的模式上产生的“波浪”效应。

附属问题:

我已经看到我的 GC Collection 2 Heap 非常大,并且遵循与我的应用程序使用的总字节数相同的模式。我想这是完全正常的,因为我们的大多数对象都会在至少 2 次垃圾回收中存活下来(例如 Singleton 类等)......你怎么看?

4

3 回答 3

1

我对几年前教的一门课做了一些研究。我不认为这些参考资料包含有关 LoH 的任何信息,但我认为无论以哪种方式分享它们都是值得的(见下文)。此外,我建议在指责垃圾收集器之前对未释放的对象引用进行第二次搜索。只需在类终结器中实现一个计数器来检查这些大对象是否如您所想的那样被丢弃。

这个问题的一个不同的解决方案是永远不要释放你的大对象,而是使用池策略重用它们。在我的狂妄自大之前,我曾多次将我的应用程序的内存需求随着时间的推移而过早地归咎于 GC,但这往往不是实现错误的症状。

GC 参考: http: //blogs.msdn.com/b/clyon/archive/2007/03/12/new-in-orcas-part-3-gc-latency-modes.aspx http://msdn.microsoft。 com/en-us/library/ee851764.aspx http://blogs.msdn.com/b/ericlippert/archive/2010/09/30/the-truth-about-value-types.aspx http://blogs。 msdn.com/b/ericlippert/archive/2009/04/27/the-stack-is-an-implementation-detail.aspx

Eric Lippert 的博客特别有趣,涉及到详细了解 C#!

于 2012-10-01T12:56:05.290 回答
1

您描述的行为是在大型对象堆 (LOH) 上创建的对象的典型问题。但是,您的内存消耗似乎稍后会恢复到较低的值,因此请检查两次是否真的是 LOH 问题。

您显然知道这一点,但不太明显的是 LOH 上的对象大小存在异常。

如文档中所述,大小超过 85000 字节的对象最终会出现在 LOH 上。但是,由于某种原因(可能是“优化”),长度超过 1000 个元素的双精度数组也最终出现在此处:

double[999] smallArray = ...; // ends up in 'normal', Gen-0 heap
double[1001] bigArray = ...; // ends up in LOH

这些数组可能会导致 LOH 碎片化,这需要更多内存,直到出现内存不足异常。

我对此感到很恼火,因为我们有一个应用程序接收一些传感器读数作为双精度数组,这导致 LOH 碎片整理,因为每个数组的长度略有不同(这些是各种频率的实时数据读数,由非实时过程采样)。我们通过实现自己的缓冲池解决了这个问题。

于 2012-10-01T12:03:19.653 回答
0

这是我的一些调查的更新:

在我们的应用程序中,我们使用大量线程来执行不同的任务。其中一些线程具有更高的优先级。

1)我们正在使用并发的 GC,我们试图将其切换回non-concurrent

我们已经看到了戏剧性的进步:

  • 垃圾收集器被频繁调用,似乎当被更频繁地调用时,它释放的内存要好得多。

一旦我有一个很好的截图来说明这一点,我就会发布一个截图。

我们在 MSDN 上找到了一篇非常好的文章。我们还在SO上发现了一个有趣的问题。

在下一个 Framework 4.5 中,有 4 种可能性可用于 GC 配置。

  1. 工作站 - 非并发
  2. 工作站 - 并发
  3. 服务器 - 非并发
  4. 服务器 - 并发

我们将尝试切换到“服务器 - 非并发”和“服务器 - 并发”,以检查它是否为我们提供了更好的性能。

我将根据我们的发现更新此线程。

于 2012-10-05T12:07:59.023 回答