4

我正在开发一个应用程序,该应用程序可能具有较大的内存负载(> 5gb),但由于客户部署环境,它需要在基于 32 位和 .NET 2 的桌面上运行。到目前为止,我的解决方案是为这些大容量对象使用应用程序范围的数据存储,当一个对象被分配给存储时,存储检查应用程序的总内存使用量,如果它接近限制它将开始将存储中的一些旧对象序列化到用户的临时文件夹,并在需要时将它们检索回内存中。这被证明是绝对不可靠的,就像应用程序中的其他对象开始使用内存一样,存储没有提示清理和腾出空间。我确实看过使用弱指针来保存内存中的数据对象,当它们被释放时它们被序列化到磁盘,

我应该使用任何有用的模式/范式来处理这个问题吗?我已经广泛搜索,但还没有发现任何有用的东西。

4

3 回答 3

4

我认为虚拟内存应该让你在这种情况下得到保障?

无论如何,似乎怀疑您在任何给定时刻确实需要内存中的所有 5gb 数据——您不可能在任何给定时间处理所有这些数据——至少在听起来像消费类 PC 的设备上是这样。您没有详细介绍您的数据,但在我看来,对象本身的设计很糟糕,因为您需要整个集合都在内存中才能使用它。您是否考虑过尝试将数据分成更合理的单元 - 然后在需要处理数据之前从磁盘进行一些抢先式加载?通过这种方式,您基本上会付出更稳定的性能权衡,但您会减少当前的颠簸问题。

于 2010-10-17T18:12:35.203 回答
2

也许您会选择管理内存映射文件并查看此处。在 .NET 2.0 中,您必须使用 PInvoke 来执行该功能。从 .NET 4.0 开始,您就拥有了MemoryMappedFile的高效内置功能

也看看:http: //msdn.microsoft.com/en-us/library/dd997372.aspx

您无法有效地将 5GB 数据存储在内存中。在 32 位操作系统中每个进程有 2 GB 限制,在64 位 Windows-on-Windows中每个 32 位进程有 4 GB 限制

所以你有选择:

  • 采用 Google 的 Chrome 方式(和 FireFox 4)并在进程之间维护一些数据。如果您的应用程序在 64 位操作系统下启动并且您有某些理由将应用程序保持为 32 位,则它可能适用。但这不是那么容易的方法。如果您没有 64 位操作系统,我想知道您从哪里获得 >5GB 的 RAM?

  • 如果您有 32 位操作系统,那么任何解决方案都将是基于文件的。当您尝试将数据保存在内存中时(通过我想知道您如何在 32 位和每个进程限制 2 GB 的内存中处理它们)操作系统只是不断地将部分数据(内存页面)交换到磁盘并在您时一次又一次地恢复它们访问它。您会遭受很大的性能损失,并且您已经注意到了(我从您的问题描述中猜到了)。主要问题操作系统无法预测您何时需要一个数据以及何时需要另一个数据。因此,它只是试图通过在磁盘上/从磁盘上读取和写入内存页面来做到最好。

    因此,您已经以低效的方式间接使用磁盘存储,MMF 只是以高效和可控的方式为您提供相同的解决方案。

您可以重新构建您的应用程序以使用 MMF,操作系统将帮助您进行高效缓存。自己进行快速测试 MMF 可能足以满足您的需求。

无论如何,除了基于文件的之外,我没有看到任何其他解决方案可以处理大于可用 RAM 的数据集。并且通常更好地直接控制数据操作,尤其是当数据量如此之大并且需要处理时。

于 2010-10-17T18:35:17.893 回答
-1

当您必须存储大量数据并保持可访问性时,有时最有用的解决方案是使用数据库等数据存储和管理系统。数据库(例如 MySQL)可以存储许多典型的数据类型,当然也可以存储二进制数据。也许您可以将对象存储到数据库(直接或通过编程业务对象模型)并在需要时获取它。这个解决方案有时可以解决数据管理(移动、备份、搜索、更新......)和存储(数据层)的许多问题——而且它与位置无关——也许这个观点可以帮助你。

于 2010-10-17T18:20:30.073 回答