繁体   English   中英

Memory 大小可通过虚拟 Memory 与 RAM 实现

[英]Memory size feasible via Virtual Memory vs RAM

我正在尝试实例化一个巨大的ArrayList

List<Integer> list = new ArrayList<Integer>(Integer.MAX_VALUE);  

在 eclipse 中运行它,我得到:

java.lang.OutOfMemoryError: Requested array size exceeds VM limit  

如果我做:

List<Integer> list = new ArrayList<Integer>(Integer.MAX_VALUE - 2);  

我得到一个不同的错误:

Java HotSpot(TM) 64-Bit Server VM warning: INFO: os::commit_memory failed; error='The paging file is too small for this operation to complete'   

#
# there is insifficent memory for the Java Runtime Environment to continue.   

我在 eclipse 的运行配置中使用以下设置启动程序:
-Xmx8G

那么这里的问题是什么? 即使我增加到-Xmx16G它仍然给出相同的错误

更新
我有点困惑,RAM的实际大小在这里重要吗? 由于分页,进程不能访问无限的虚拟 memory 吗?

我有点困惑,RAM的实际大小在这里重要吗?

是的,它确实。

由于分页,进程不能访问无限的虚拟 memory 吗?

是的,他们确实...以您需要磁盘空间来保存虚拟 memory 页面为模。 确实,“那*就是您收到此错误的原因:

The paging file is too small for this operation to complete.

这个“修复”是使页面文件更大。 这必须在操作系统级别完成。

但是,分页意味着操作系统必须在需要时将页面从磁盘复制到 memory。 为了给它们腾出空间,它必须将其他(脏)页面从 RAM 复制到磁盘。 所有这些复制都使用 CPU 和磁盘 I/O 带宽并减慢您的程序。

一个典型的 (C/C++) 程序通常可以在一定程度上解决这个问题,具体取决于应用程序的 memory 访问模式。 但是在 Java 中你会遇到 GC 偶尔运行的问题。 在一段时间内,GC 将以(基本上)随机顺序访问大量页面中的对象。 对于“完整”的垃圾收集来说,情况更糟。

如果应用程序正在访问的页面集(即“工作集”)的大小大于可用 RAM 页面的数量,则您可能会“崩溃”; 即通过页面的读取和写入使 I/O 系统饱和。 这对性能来说真的很糟糕。 在极端情况下,它会使操作系统无响应。

因此,使用大于可用物理 RAM 的堆运行 Java 应用程序是一件有潜在危险的事情。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM