在64位系统上创建一个非常大的数组的缺点是什么

What would be the disadvantage of creating an array of really big size on 64 bit systems?

本文关键字:一个 非常 数组 是什么 缺点 系统 64位 创建      更新时间:2023-10-16

诸如Linux之类的操作系统在写入原则上工作,因此,即使您分配了100 GB的数组,但只能使用10GB,您也只会使用10 GB的内存。那么,创建如此大的数组的缺点是什么?不过,我可以看到一个优势,这是您不必担心使用动态数组,这将具有重新分配的成本。

主要缺点是,通过执行此操作,您对标准库分配器的确切方式做出了有力的假设 1 和基础Linux分配器起作用。实际上,分配器和基础系统并不总是像您提到的那样工作。

现在,您提到了"写作复制",但是您可能真正指的是懒惰页面总体和过度承诺的组合。取决于配置,这意味着您分配但不要触摸的任何内存都可能不符合内存限制,并且可能不会占据物理内存。

问题是,这通常可能不起作用。例如:

  • 许多分配器都有触摸分配的内存的模式,例如,在调试模式下以已知模式填充它,以帮助诊断对非初始化内存的引用。大多数分配器在分配的区域之前至少触摸一些字节来存储可用于DealLocation的元数据。因此,您对可能破裂的分配行为做出了有力的假设。
  • Linux超越行为是完全可配置的。实际上,许多服务器端Linux用户将禁用它,以减少与OOM杀手有关的不确定性和不可恢复的问题。因此,您的说法仅对于某些过度使用的配置而言,对Linux的行为懒惰才是正确的。
  • 您可能会假定内存是在4K块中投入的,并围绕它调整算法。但是,系统具有不同的页面尺寸:16K和64K并不少见,因为X86 Linux Systems默认启用了透明的巨大页面,因此实际上您可能会在没有意识到的情况下获得2,048K页面!在这种情况下,您可能最终会根据您的访问模式进行几乎整个数组。
  • 如评论中所述,这种使用的"失败模式"非常差。您认为您只使用阵列的一小部分,但是如果您最终使用的是系统所能处理的更多,则最多可以在某些随机访问新页面上向应用程序发出信号,但更像是OOM杀手只会在您的机器上杀死其他随机过程。

1 在这里,我假设您正在使用 mallocnew之类的东西来分配数组,因为您没有直接提及 mmap或任何东西。

现实世界中的操作系统不仅允许您的程序访问所有可用的内存 - 它们执行配额。因此,一个64位操作系统,在硬件上运行,具有足够的物理内存,只会拒绝将所有内存分配给任何程序。如果您的操作系统已虚拟化,这将更加正确(例如,某些Hypervisor托管了同一物理平台上的两个或多个操作系统 - 每个托管操作系统的Hypervisor执行配额,其中一个将为您的程序执行配额)。<<<<<<<<<<)。/p>

尝试分配大量内存是一种有效的方法,是使操作系统不允许您的程序所需内存的可能性最大化。

是的,是的,管理员有可能增加配额,这也有后果。如果您没有管理访问权限,则需要说服管理员增加这些配额(除非您的计算机只有一个用户,否则这不一定很容易)。消耗大量内存的程序可能会导致其他程序饿死,如果您自己或其他人需要其他程序,这将成为一个问题。在极端情况下,您的程序可能会饿死操作系统的资源本身,这会导致其及其托管的所有程序减速,并损害系统稳定性。这些担忧就是为什么系统首先执行配额的原因 - 通常默认情况下。

也可能出现问题,因为操作系统可以配置为过度命令。宽松地说,这意味着,当程序请求内存时,操作系统告诉程序分配已成功,即使操作系统尚未分配。随后,当程序使用该内存(通常,将数据写入其中)时,突然需要操作系统才能真正使内存可用。如果操作系统出于任何原因无法执行此操作,那将成为程序的问题(认为它可以访问内存,但操作系统可以防止访问)。这通常会导致某些错误条件影响程序执行(并且通常导致程序终止)。虽然与施加过度相关的问题可能会影响任何程序,但是当程序分配大量内存时,几率明显增加。