如何在 Java 中查看堆中的内容?

Posted

技术标签:

【中文标题】如何在 Java 中查看堆中的内容?【英文标题】:How can I see what is in my heap in Java? 【发布时间】:2008-09-28 14:15:21 【问题描述】:

我已经设法在我正在开发的 Java 应用程序中发现内存“泄漏”。在运行我的 JUnit 测试套件时,我随机出现内存不足异常 (java.lang.OutOfMemoryError)。

我可以使用哪些工具来检查我的 Java 应用程序的堆,以查看我的所有堆都用完了什么,这样我就可以弄清楚是什么保留了对应该能够被垃圾回收的对象的引用。

【问题讨论】:

【参考方案1】:

VisualVM 包含在最新版本的 Java 中。您可以使用它来创建堆转储,并查看其中的对象。

或者,您也可以使用 jmap(在您的 jdk/bin 目录中)创建 heapdump commandine:

jmap -dump:format=b,file=heap.bin <pid>

您甚至可以使用它来快速获取所有对象的直方图

jmap -histo <pid>

我可以推荐 Eclipse Memory Analyzer (http://eclipse.org/mat) 来进行堆转储的高级分析。它可以让您准确找出某个对象或一组对象存在的原因。这是一个博客条目,向您展示了 Memory Analyzer 可以做什么:http://dev.eclipse.org/blogs/memoryanalyzer/2008/05/27/automated-heap-dump-analysis-finding-memory-leaks-with-one-click/

【讨论】:

Visual VM 和 Netbeans Profiler 允许您执行与 EMA 相同的操作。 我不知道netbeans,但我肯定没有在visual vm中找到'gc root的最短路径'。【参考方案2】:

如果你需要免费的东西,试试VisualVM

来自项目的描述:

VisualVM 是一个集成了命令行 JDK 工具和轻量级分析功能的可视化工具。专为开发和生产时间使用而设计。

【讨论】:

【参考方案3】:

这是一个很老的问题。自从最初回答以来,很多人可能已经开始使用 IntelliJ。 IntelliJ 有一个名为JVM Debugger Memory View 的插件可以显示内存使用情况。

【讨论】:

在使用了一些不同的工具之后,我发现 IntelliJ 也有一个plugin for VisualVM(在不同的答案中提到)。这种组合最终对我来说效果最好。【参考方案4】:

使用Eclipse Memory Analyzer

据我所知,在分析堆转储时,没有其他工具可以接近它的功能、性能和价格(免费和开源)。

【讨论】:

【参考方案5】:

使用像 JProfiler 或 YourKitProfiler 这样的分析器

【讨论】:

【参考方案6】:

JProfiler 对我来说效果很好....

http://www.ej-technologies.com/products/jprofiler/overview.html

【讨论】:

【参考方案7】:

如果您使用的是支持 GTK 的系统,您可以尝试使用JMP。

【讨论】:

【参考方案8】:

您可以试用 JRockit Mission Control 工具套件中的 Memory Leak Detector。它允许您在 JVM 运行时检查堆。您不需要一直拍摄快照。您可以在线连接到 JVM,然后查看堆在垃圾收集之间的变化。您还可以检查对象、以图形方式跟踪引用并从应用程序当前分配对象的位置获取堆栈跟踪。这是一个简短的introduction。

该工具可免费用于开发,您可以下载它here。

【讨论】:

以上是关于如何在 Java 中查看堆中的内容?的主要内容,如果未能解决你的问题,请参考以下文章

如何判断一个对象是创建在栈中还是堆中

手写 asm.js - 你如何跟踪堆中的 javascript 对象?

如何在二进制堆中存储任何类型的可比较对象

如何在.Net中列出堆中的所有托管对象?

Java指针

Java中“==”与equals通俗易懂篇