使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

时间:2024-03-21 11:36:49

如何检测和分析内存泄漏?

我们在项目开发过程中就一直使用的LeakCanary检测内存泄漏,附上链接:https://github.com/square/leakcanary ,这个特别棒,在开发阶段发现内存泄漏就能实时更改了,避免了到项目后期再花费时间额外排查内存泄漏,就是这么溜!

一、说说使用Android Studio自带的Dump Java Heap如何排查内存泄漏,或者优化内存使用情况:

1、打开Android Monitor,选中设备和应用包名,点击Dump Java Heap:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

2、生成.prof文件:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

3、打开Captures,可以从View—Tool Windows—Captures打开:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

4、打开右侧的Analyzer task,默认选中分析内存泄漏和重复定义的字符串,点击绿色的启动按钮:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

5、可以看到重复定义的变量,有无内存泄漏的Activity,此外,AS自带的hprof查看工具会列出类、类的实例和实例的引用树,hprof文件下各列分别代表那些信息呢?

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

根据这些信息我们就可以分析具体的内存使用细节了,以此来帮助你跟踪内存的使用情况,找出内存泄漏的地方。

二、使用MemoryAnalyzer分析内存

1、使用MemoryAnalyzer打开.prof文件,需要先将AS生成的.prof文件转化为标准的prof文件:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

2、转换完保存到指定路径下,最好是新建一个文件夹,待会MemoryAnalyzer打开该文件会在同一目录下生成多个文件。

3、接下来,打开MemoryAnalyzer,附上官方下载链接:http://www.eclipse.org/mat/downloads.php

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

4、File—Open Heap Dump,选择刚才转换的标准prof文件,打开:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

5、MAT内存分析结果就出来了,overview通过饼状图展示了内存的当前使用情况,并且指出疑似内存泄漏的地方,但不一定真的就是内存泄漏,只是很好的定位了占用内存多的地方。

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

6、点击 Histogram 显示 

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

7、通过类名过滤,输入后回车:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

8、过滤结果:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

9、选中某一项,右键—进行如下操作:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

10、得到如下结果:

使用Android Studio的Dump Java Heap和MemoryAnalyzer分析内存泄漏

11、具体的就根据自己项目情况进行分析解决了,补充:

Histogram:列出内存中的对象,对象的个数以及大小。

Dominator Tree:列出最大的对象以及其依赖存活的Object (大小是以Retained Heap为标准排序的)。

Top Consumers:通过图形列出最大的object。

Shallow heap:无序列表1 Shallow size就是对象本身占用内存的大小,不包含其引用的对象。针对非数组类型的对象,它的大小就是对象与它所有的成员变量大小的总和。当然这里面还会包括一些java语言特性的数据存储单元。针对数组类型的对象,它的大小是数组元素对象的大小总和。

Retained Heap:它表示如果一个对象被释放掉,那会因为该对象的释放而减少引用进而被释放的所有的对象(包括被递归释放的)所占用的heap大小。(间接引用的含义:A->B->C, C就是间接引用。不过,释放的时候还要排除被GC Roots直接或间接引用的对象。他们暂时不会被被当做Garbage)

参考:https://blog.csdn.net/junhuahouse/article/details/79731529

http://wensong.iteye.com/blog/1986449