2010-09-17 64 views
0

我写了一个非常复杂的java应用程序,它正在对来自市场的价格数据进行大量实时计算,并从查看Windows中的任务管理器这个吸盘正在接近1MEG,每30秒钟一次,性能一直很好,直到它接近300MEG的内存限制,然后g-collector真的踢进我的CPU达到50%左右,并且UI性能迅速降低到目前为止我写的所有内容这听起来像我有一些不好的代码正在进行,因为我的程序的性质是CPU密集型的,但设计存储内存中的数据非常少。有很多内存问题的Java应用程序

我需要一些帮助,以了解如何才能找出问题所在,我想如果我能看到哪些对象被存储在内存中,可能会有帮助一些糟糕的代码,但我心中有了Java,因为我认为这些都是我不必担心的问题。感谢任何答案。 - Duncan

+1

使用探查器可能是您最好的选择。 – jjnguy 2010-09-17 19:07:28

+0

尝试VisualVM和jmap -histo,如果你想要更多的细节,请试用YourKit的eval许可证。我建议你使用“jstat -gccause {pid} 5s”来监视内存使用情况,因为这样可以得到更准确的图片。 – 2010-09-17 20:08:32

回答

4
  1. 确定一些合理的性能目标(内存使用率,吞吐量,延迟)。
  2. 把一些可重复的性能测试放在一起,越接近你可以让这些现实生活场景越好。
  3. 抓住一个好的分析器。我已经使用YourKit取得了很大的成功,Netbeans和Eclipse profilers也不错。大多数体面的配置文件将能够识别内存使用情况,GC和性能热点。
  4. 找出最大的罪魁祸首,并开始修复从列表的TOP开始的问题。
1

检出VisualVM。它位于jvisualvm当前的JDK bin目录中。如果您没有内存泄漏,那么在运行垃圾回收器时堆的使用率应该降低,并且可以通过计算堆中对象的保留大小来查看哪些对象可能拥有内存。

http://download.oracle.com/javase/6/docs/technotes/guides/visualvm/intro.html

+0

我暗示的是通过确保垃圾收集器正在回收内存来确保它不是内存问题。 – jbindel 2010-09-17 19:35:37

+0

谢谢你的回复,我会看看是否可以将它与eclipse中启动我的程序联系起来,如果它涉及的是JVM参数,那么我认为这是最简单的解决方案,而不是首先试图获得eclipse分析工具已下载并在我的IDE中工作 - Duncan – 2010-09-17 21:00:54

0

与其他人一样说,使用一个分析器找到什么在占用内存。

如果您还不知道,垃圾收集器只能释放超出范围的对象的内存。也就是说,没有任何对它们的引用。只要确保它完成后就会超出范围。这听起来像是你用某种方式锁定了它,但它仍然在某处被引用。

另外,如果你想建议,它清理GC,试试这个:

的System.gc();
System.runFinalization();

同样,这只是对gc的一个建议;但是如果你在之后运行它,我发现它确实有帮助,很多对象超出了范围。

最后,你可以调整你的虚拟机参数。 有最小/最大堆大小设置的设置。如果它是一个关键应用程序,将它们设置为相同并将其设置为高(这样就不必保持分配/解除分配 - 它只是在启动时抓取一个大块)。这不是一个解决方法,只是一种解决方法。