2010-01-22 79 views
11

注意:我知道Memory management in memory intensive application这个问题,但是这个问题似乎是关于频繁分配内存的应用程序,而我的问题是关于应用程序故意设计为消耗尽可能多的物理内存这是安全的。针对有意识内存密集型应用程序的内存管理

我有一个服务器应用程序,使用大量的内存来执行缓存和其他优化(想想SQL Server)。应用程序运行在专用计算机上,因此可以(也应该)消耗尽可能多的内存,以便加速并提高吞吐量和响应时间,而无需担心会影响系统上的其他应用程序。

问题是,如果内存使用率被低估,或者如果负载增加,可能会因为内存分配失败而导致严重故障 - 在这种情况下,最好的办法是释放内存以防止以牺牲性能为代价的失败。

一些假设:

  • 应用在专用机器上运行
  • 应用程序的内存需求超过计算机上的物理内存(也就是说,如果额外的内存用于应用它将始终能够使用该内存以某种方式提高响应时间或吞吐量)
  • 内存的有效管理方式使内存碎片不成问题。
  • 应用程序知道可以安全释放哪些内存,以及为了最小的性能影响首先释放哪些内存。
  • 在Windows计算机上的应用程序运行

我的问题是 - 我应该怎么处理内存分配在这样的应用程序?尤其是:

  • 如何预测内存分配是否会失败?
  • 为了确保核心操作系统操作保持响应(并且不会以这种方式对应用程序性能产生不利影响),我应该留出一定的内存空间吗?我该如何找出多少内存?

的核心目标是防止故障如使用过多内存,而在同一时间使用了尽可能多的内存可能的结果。

我是C#开发人员,但我希望任何这样的应用程序的基本概念都是相同的,不管语言如何。

+0

顺便说一句 - 因为虚拟与物理内存的复杂性,我一直有意使用术语“内存”的大小。出于同样的原因,我没有提到32位和64位。 – Justin 2010-01-22 13:31:06

回答

1

在linux中,内存使用百分比分为以下几个级别。

0 - 30% - 不交换 30 - 60% - 仅交换脏页面 60 - 90% - 交换干净页面也基于LRU策略。

90% - 调用OOM(内存不足)杀手并终止消耗最大内存的进程。

检查这一点 - http://linux-mm.org/OOM_Killer

在心里想着窗口可能也有类似的政策,这样你就可以检查内存统计,并确保你永远不会得到最大阈值。

停止消耗更多内存的一种方法是进入睡眠状态,给内存清理线程运行更多时间。

0

这是一个非常好的问题,也必然是主观的,因为C#的基本特性就是所有的内存管理都是由运行时完成的,即垃圾收集器。垃圾收集器是一个非确定性的实体,它管理和扫描回收的内存,取决于内存被分割的频率,GC将会启动,因此事先知道并不是件容易的事情。

要正确地管理内存听起来乏味但常识的适用,如using子句,以确保对象被处置。您可以放入一个处理程序来捕获OutOfMemory Exception,但这是一种尴尬的方式,因为如果程序内存不足,程序是否会抓​​住并炸毁,或者是否应耐心等待GC启动,再次确定这是棘手的。

系统的负载可能会对GC的工作产生不利影响,几乎到了拒绝服务的地步,因为机器的规格或者机器的规格是什么,所有的一切都只是停顿而已,机器的工作是未知的,我不能完全回答,但我会假设它有负载的RAM ..

从本质上讲,虽然一个很好的问题,我认为你不应该担心它,并把它留给.NET CLR处理内存分配/碎片,因为它似乎做得很好。

希望这会有所帮助, 最好的问候, 汤姆。

0

你的问题让我想起了旧的讨论"So what's wrong with 1975 programming ?"varnish-cache的架构师认为,与其告诉操作系统摆脱困境并自己管理所有内存,您应该更愿意与操作系统合作,并让它理解您打算如何处理内存。

例如,不是简单地从磁盘读取数据,而应该使用memory-mapped files。这使得操作系统可以应用其LRU算法在内存变得稀缺时将数据写回磁盘。同时,只要有足够的内存,您的数据将保留在内存中。因此,您的应用程序可能会使用所有内存,而不会冒死亡的风险。