作为一个大型实验的一部分,我试图在集群上运行NetLogo(一个java模拟框架)模拟。我对一个(相对)简单的模拟似乎需要大量的内存感到惊讶。在集群上,它抛出“java.lang.OutOfMemoryError:Java堆空间”异常,任何小于“-Xmx 2500 M”的堆大小。一次执行需要5个小时。我在我的两台Mac(iMac和MacBook Pro)上运行了相同的实验,它们在不到一个小时的时间内执行,“-Xmx 1024”没有给出错误。集群作业需要“-XX:MaxPermSize= 250 M”,而在我的Mac上不需要超过默认值。我在所有情况下都运行了相同的代码,相同的输入,使用完全相同的jar。
在每种情况下都使用64位JVM(据我所知,它们非常相似):
<on the cluster>
$ java -version
java version "1.6.0_26"
Java(TM) SE Runtime Environment (build 1.6.0_26-b03)
Java HotSpot(TM) 64-Bit Server VM (build 20.1-b02, mixed mode)
<on my macs>
$ java -version
java version "1.6.0_31"
Java(TM) SE Runtime Environment (build 1.6.0_31-b04-415-10M3646)
Java HotSpot(TM) 64-Bit Server VM (build 20.6-b01-415, mixed mode)
而且我在所有情况下都在运行客户端JVM(最初是在集群上使用服务器,切换到客户端没有区别)。我已经尝试过在集群上使用java 7执行,同样的巨大内存和执行时间问题。
我完全困惑了,没有人和我谈过话可以解释这个。有没有人以前遇到过这个?任何帮助都非常感谢!
2条答案
按热度按时间kxxlusnw1#
我怀疑其中一个有更快的网络或磁盘IO。如果您使用队列写入磁盘或写入网络,其中一台计算机可以跟上,但另一台不能,队列可能会增长,使计算机变慢,并使用无限数量的内存。
如果您的网络IO速度更快,则可能有助于更快地发送数据(保持队列较小),也可能意味着您接收数据的速度过快(意味着队列的增长速度可能快于其消耗速度)
这在很大程度上取决于你的应用程序实际上做了什么。当你的程序得到一个OOME时,我建议你得到一个堆转储,分析它,寻找消耗大量内存的集合(例如队列)。
zf9nrax12#
我怀疑问题出在你使用的是服务器JVM。客户端JVM在64位机器上不可用。即使你要求客户端JVM,它也会给予你服务器JVM。