如何使用 Netbeans 分析器查找内存泄漏?[已关闭]
我想在我的 java 应用程序中查找内存泄漏,但我不知道如何使用 Netbeans profiler 来执行此操作。
我想在我的 java 应用程序中查找内存泄漏,但我不知道如何使用 Netbeans profiler 来执行此操作。
由于此处的一些链接有点过时,并且针对 NetBeans 6.0,因此下面是一些更新,用于在使用 Netbeans 6.8 的 Java 桌面应用程序中插入内存泄漏。
首先,您需要对应用程序执行广泛的搜索,以查找可能泄漏内存的一般区域/功能。因此,通过选择以下选项启动 NetBeans 分析器:
型材->型材项目(项目名称)
然后按如下方式设置探查器:
因此,你可以查看何时泄漏内存,为了帮助指导搜索,请调出遥测概述(在下图中标记为 A)。
在执行广泛搜索时,您希望继续运行一堆步骤,这些步骤使您的应用程序从执行某些操作返回到原始的“干净”状态。在我的情况下,我几乎将一些数据插入到我的应用程序中(file->open),显示它(显示),然后全部清除(file->new)。在我完成文件>new之后,我期望使用的堆和幸存的世代数与我开始时相同......如果垃圾回收器运行后它们仍然很高,则表示您泄漏了一点内存。
现在,您已经在应用程序中发现了一个泄漏内存的功能,现在是时候缩小搜索范围并确切地找出仍在引用的对象。这是在 NetBeans 探查器中通过获取“堆转储”来完成的:
配置文件 -> 采取堆转储...
这将在摘要页面上显示堆,切换到类视图并通过输入根包名称(即:org.yourproject)来筛选项目类,按实例[%]排序,您将拥有消耗最多内存的对象:
现在,运行您在广泛搜索期间发现泄漏的往返步骤,并执行另一个堆转储:
配置文件 -> 采取堆转储...
通过比较这两个列表,查找第二个转储中实例数多于第一个转储的类。具有更多实例的类可能是泄漏内存的类。在第二个转储文件中,双击可能是泄漏的类,以在实例视图中显示它:
左侧下方是您双击的特定类的所有实例,如果选择一个实例,则其字段和引用将填充在右侧。由于我们怀疑此对象可能正在泄漏,因此某些内容必须仍然包含对它的引用。右键单击参考列表中的“this”,然后选择“显示最近的GC根”。如果对话框返回“未找到GC根目录”,则表示Java虚拟机下次将对其进行垃圾回收,并且该对象不对泄漏的内存负责。然而,如果这棵树膨胀了,那么这可能是漏水的罪魁祸首之一。
此步骤的关键是从列表顶部向下工作。在上图中,IntDataValue 是我们认为泄漏的对象,树中的下一件事是引用它的对象。字段是保存引用的变量,类型是保存引用的对象的类型。在列表中工作时,请继续轻拂源代码,并问自己以下问题:
为什么这是一个参考?
它应该持有一个参考吗?
在树上行走时,经常问自己这些问题,我经常发现运行调试器并单步执行代码是找到答案的唯一方法。
以上是我用来缩小搜索范围的原始机制,但我找到了另一种方法来帮助缩小搜索范围,方法是使用“Compre内存快照...”功能在“配置文件”菜单中。首先拍摄快照(见截图)。
现在,运行在广泛搜索期间发现泄漏的往返步骤,并拍摄另一个快照。将它们保存在可以使用“另存为”找到它们的地方...按钮。
选择配置文件 ->比较内存快照...
选择两个快照,小心地将第一个快照放在顶部插槽中,将第二个快照放在底部插槽中(否则您将获得不正确的负内存更改):
这将生成一个类似于以下内容的屏幕,其中字节数是两个快照之间分配变化的大小(即,大量增长可能是可疑的内存泄漏,以及分配数的变化):
网络上有几个资源可以为您提供帮助
http://www.javapassion.com/handsonlabs/nbprofilermemory/
http://www.netbeans.org/kb/articles/nb-profiler-uncoveringleaks_pt1.html
http://kirk.blog-city.com/more_on_memory_leaks.htm
简而言之,您可以监视“幸存的生成器”,即应用程序保存在内存中的对象。
当您看到此指标失控时,可以切换到 Memory Live 分析模式,按幸存的生成器对类进行排序,然后右键单击鼠标按钮选择“显示分配堆栈跟踪”选项