使用硬盘 Space 作为 Java 堆?
Using Hard Disk Space as Java heap?
我正在尝试 运行 一个 jar 文件,它在 运行 一段时间后给出 'out of memory error'。我有时会搜索有关使用硬盘 space 作为 java 堆的信息,但大多数解决方案都建议优化代码或使用类似 'Ehcache' 的东西。但问题是,我只有jar文件,并没有写它的代码。所以,我的问题是我可以使用一些机制或软件,通过它我可以让java使用硬盘space作为堆,而不需要修改jar文件的代码有什么办法吗?
您不能将硬盘 space 用于 运行 java 程序,
你可以做两件事:
使用以下命令增加堆内存
java-Xmx1024m-jarTest.jar
Use Java8 使用 metaspace 使用本机内存
https://dzone.com/articles/java-8-permgen-metaspace
我假设您有一个 Java 类 的 JAR 文件,但没有附带源代码。这当然是有问题的,但是了解那些 类 正在做什么对你来说很重要,因为如果存在一些无法克服的内存泄漏是那些 类 导致的(是的,Java 确实有内存泄漏以所谓的意外对象保留的形式)那么后续的努力可能仍然不足。
话虽如此,应该注意的是,JVM(特别是 Oracle JVM)在您希望它使用多少 heap 内存方面提供了一些可配置性运行 您的 Java 应用。最重要的配置参数是 -Xmx
,即所谓的 "Maximum Heap Memory"。当您指定此参数时,例如-Xmx6g,JVM,在启动时,将向操作系统(JVM 运行s)请求那么多内存。具体细节有点复杂,但如果在启动时该内存量不可用,则 JVM 启动失败。有复杂的算法来确定此堆内存的 default 值,但如果您有要求,您应该像上面那样覆盖默认值。在上述情况下,您的 JVM (java -Xmx6g -jar test.jar
) 要求 6 GB 的堆开始。
确定 JVM 在其生命周期内所需的堆内存的正确值在某种程度上是一门艺术,尽管您可以考虑几件事情。最重要的是了解您应用的 运行 时间特征。您应该知道如何以及何时分配和释放对象(以便垃圾收集器 启动 ),这样您就不会 运行 超出堆 space当 JVM 向 OS 发出下一个分配请求时。在我看来,这就是您的情况 - 某处正在构造一堆对象,需要 OS 没有的内存。
显然,OS 将尝试查看是否有那么多物理 RAM 可用,如果可用,JVM 的请求将被批准。这就是幸福的道路。
然而,由于没有足够的 RAM 可用,这条快乐的道路并不总是可行的。即便如此,OS 仍可以批准请求,因为这个 OS 概念称为 虚拟内存 。无需深入了解太多细节(您可以阅读虚拟内存),只需说 OS 有一种机制,它可以通过 [= 的机制将硬盘 space 用作 RAM 32=]页面交换。换句话说,它可以将数据交换到物理 RAM 或将数据交换到硬盘,其方式对所有进程 运行 都透明(包括 JVM,它只不过是一个名为 运行 的进程) =12=]).
这就是您的系统管理员技能对您有帮助的地方。有一些方法可以增加 OS 上的交换 space。例如,在 Linux 上,您可以使用 swapon 命令来执行此操作。这将不可避免地导致一种称为 thrashing 的现象,但这是您能做的最好的事情(您也可以摆脱其他程序以节省内存)。
同样,这可能只会让您 到此为止。如果您的程序中存在内存泄漏,再多的 GC(回收未使用的内存,这是 JVM 的一个重要特性)或交换 space 都可能对您有所帮助,迟早您会遇到可怕的 OutOfMemoryError
.
您应该考虑指定 -XX:HeapDumpOnOutOfMemoryError 以查看发生此错误时 JVM 正在做什么。
我正在尝试 运行 一个 jar 文件,它在 运行 一段时间后给出 'out of memory error'。我有时会搜索有关使用硬盘 space 作为 java 堆的信息,但大多数解决方案都建议优化代码或使用类似 'Ehcache' 的东西。但问题是,我只有jar文件,并没有写它的代码。所以,我的问题是我可以使用一些机制或软件,通过它我可以让java使用硬盘space作为堆,而不需要修改jar文件的代码有什么办法吗?
您不能将硬盘 space 用于 运行 java 程序,
你可以做两件事:
使用以下命令增加堆内存
java-Xmx1024m-jarTest.jar
Use Java8 使用 metaspace 使用本机内存 https://dzone.com/articles/java-8-permgen-metaspace
我假设您有一个 Java 类 的 JAR 文件,但没有附带源代码。这当然是有问题的,但是了解那些 类 正在做什么对你来说很重要,因为如果存在一些无法克服的内存泄漏是那些 类 导致的(是的,Java 确实有内存泄漏以所谓的意外对象保留的形式)那么后续的努力可能仍然不足。
话虽如此,应该注意的是,JVM(特别是 Oracle JVM)在您希望它使用多少 heap 内存方面提供了一些可配置性运行 您的 Java 应用。最重要的配置参数是 -Xmx
,即所谓的 "Maximum Heap Memory"。当您指定此参数时,例如-Xmx6g,JVM,在启动时,将向操作系统(JVM 运行s)请求那么多内存。具体细节有点复杂,但如果在启动时该内存量不可用,则 JVM 启动失败。有复杂的算法来确定此堆内存的 default 值,但如果您有要求,您应该像上面那样覆盖默认值。在上述情况下,您的 JVM (java -Xmx6g -jar test.jar
) 要求 6 GB 的堆开始。
确定 JVM 在其生命周期内所需的堆内存的正确值在某种程度上是一门艺术,尽管您可以考虑几件事情。最重要的是了解您应用的 运行 时间特征。您应该知道如何以及何时分配和释放对象(以便垃圾收集器 启动 ),这样您就不会 运行 超出堆 space当 JVM 向 OS 发出下一个分配请求时。在我看来,这就是您的情况 - 某处正在构造一堆对象,需要 OS 没有的内存。
显然,OS 将尝试查看是否有那么多物理 RAM 可用,如果可用,JVM 的请求将被批准。这就是幸福的道路。
然而,由于没有足够的 RAM 可用,这条快乐的道路并不总是可行的。即便如此,OS 仍可以批准请求,因为这个 OS 概念称为 虚拟内存 。无需深入了解太多细节(您可以阅读虚拟内存),只需说 OS 有一种机制,它可以通过 [= 的机制将硬盘 space 用作 RAM 32=]页面交换。换句话说,它可以将数据交换到物理 RAM 或将数据交换到硬盘,其方式对所有进程 运行 都透明(包括 JVM,它只不过是一个名为 运行 的进程) =12=]).
这就是您的系统管理员技能对您有帮助的地方。有一些方法可以增加 OS 上的交换 space。例如,在 Linux 上,您可以使用 swapon 命令来执行此操作。这将不可避免地导致一种称为 thrashing 的现象,但这是您能做的最好的事情(您也可以摆脱其他程序以节省内存)。
同样,这可能只会让您 到此为止。如果您的程序中存在内存泄漏,再多的 GC(回收未使用的内存,这是 JVM 的一个重要特性)或交换 space 都可能对您有所帮助,迟早您会遇到可怕的 OutOfMemoryError
.
您应该考虑指定 -XX:HeapDumpOnOutOfMemoryError 以查看发生此错误时 JVM 正在做什么。