2014-03-30 30 views
1

我有关于数组和链表的概念性问题。数组和链接列表:如果512 MB空闲,但是300 MB空间不连续,阵列是否能够在内存中分配300MB

数组是连续的记忆块。

假设一个系统有1024个单位的内存。 512个单位被占用(系统+其他)。

我们的过程需要300个单位。

在内存中有512个单元可用时,最大的连续块是200单元。因此,可以有1个200个单元的块,3个100个块。

  1. 在诸如Java的语言中的数组分配会发生什么。在C中,malloc将会失败?
  2. 如果底层的数据结构是链接列表,它应该能够轻松地处理非连续性(我在这个假设中是否正确)?

  3. 操作系统会“碎片整理”内存或任何相当的?

通过记忆,我的意思是RAM。不是硬盘。

+0

这取决于你所说的“记忆”。如果它是*物理*内存碎片,操作系统提供的虚拟内存系统应该隐藏它。 –

+0

我想我的意思是,*物理内存*。虚拟内存也基于磁盘进行抽象。所以要了解它,我想知道会发生什么。它是否将内存内容写入磁盘,然后再次加载它们,但会创建一个300个单元的连续块? – Nasir

+0

操作系统永远不会对内存进行碎片整理。它支持虚拟内存,从不担心这样的问题。 –

回答

1

嗯,它有点特定于实现,但我想期望 JVM实现通过分配一个连续的内存块来初始化数组。我不想认为这是绝对必要的,但它将是迄今为止最有效的方法。

如果存储器是在所要求的形式不可用时,JVM将抛出OutOfMemoryError,具体根据JLS第15.10.2:

接着,空间被分配用于新的数组。如果没有足够的空间分配数组,则通过抛出OutOfMemoryError突然完成数组创建表达式的求值。

(JVM的应尽量先安排足够的空间,但是 - 引发错误,例如之前运行的垃圾收集和压实。)

是,链表可以应对这一切 - 但无论如何,它将需要更多的内存,因为所有额外的对象正在创建。如果您的300MB内存需求实际上是3亿字节,并且您创建了LinkedList<Byte>,则尝试创建3亿个节点将因所有对象和引用的开销而失败。至于“碎片整理” - 许多JVM都有“压缩”垃圾回收器,它们会在内存中移动对象以避免碎片。不要忘记,这是所有的虚拟内存 - 它不需要物理连续。该部分由操作系统处理,我们很少需要担心。

+0

我想这部分,我想了解的是,如果连续块不可用(内存有物理限制)会发生什么情况。 JVM做了什么?假设JVM可以访问操作系统允许的最大值(而300则小于该限制)。它如何处理数组分配? – Nasir

+0

@Nasir:如果内存不可用,则抛出“OutOfMemoryError”。 –

+0

谢谢。这是我想知道的。尽管内存是可用的,但不在连续的块中。因此引发'OutOfMemoryError'。 – Nasir