引言
欲善其事, 先利其器.
1, 一图看懂Memory Monitor
Memory Monitor 是 Android Studio内置的, 官方的内存监测工具. 图形化的展示当前应用的内存状态, 包括已分配内存, 空闲内存, 内存实时动态等.
顶部矩形指示当前调试的设备以及应用进程.
图形区域:
横向时间轴, 内存检测时间, 跟随滚动.
纵向内存轴, 内存使用量, 根据应用使用动态分配.
蓝色区域表示当前已分配使用的内存量.
灰色区域表示剩余可使用的内存量.
红色圈圈指示的是系统GC事件(内存有一定量的回收).
工具栏:
① GC按钮, 点击执行一次GC操作.
② Dump Java Heap按钮, 点击会在该调试工程的captures目录生成一个类似这样”com.anly.githubapp_2016.09.21_23.42.hprof”命名的hprof文件, 并打开Android Studio的HPROF Viewer显示该文件内容.
③ Allocation Traking按钮, 点击一次开始, 再次点击结束, 同样会在captrures目录生成一个文件, 类似”com.anly.githubapp_2016.09.21_23.48.alloc”, alloc后缀的文件, 并打开Allocation Tracker视图展示该文件内容.
2, 使用HPROF Viewer & Analyzer来分析hprof文件
Memory Monitor通过Dump Java Heap可以生成一个hprof的文件, 这个文件是Android特定的Heap和CPU分析文件, 记录了这段时间内的Java Heap变化.
2.1 关于Java Heap
由Java Heap文件可以看到如下数据:
按类型显示对象申请的内存快照(内存大小);
每次自动或手动触发GC时的样本数据;
协助定位可能发生的内存泄露点:
所有已经被destroyed的activity, 还可以从GC Root访问到.
重复的String实例.
2.2 HPROF Viewer怎么看
HPROF Viewer分成三个大块, 分别介绍下:
2.2.1 Class View
图中标①的View.
显示当前选中的Heap中的所有Class. 上方有两个可选列表, 分别是用来选择Heap区域, 和Class View的展示方式的.
Heap类型分为:
App Heap – 当前App使用的Heap
Image Heap – 磁盘上当前App的内存映射拷贝
Zygote Heap – Zygote进程Heap(每个App进程都是从Zygote孵化出来的, 这部分基本是framework中的通用的类的Heap)
可选展示方式:
Class List View – 类列表方式
Package Tree View – 根据包结构的树状显示
列 | 解释 |
---|---|
Class Name | 类名 |
Total Count | 该类的实例个数 |
Heap Count | 选定的Heap中该实例的个数 |
Sizeof | 每个该实例占用的内存大小 |
Shallow Size | 所有该类的实例占用的内存大小 |
Retained Size | 该类的所有实例可支配的内存大小 |
2.2.2 Instance View
图中标②的View.
根据在Class View中选中的Class, 列表方式展示其所有实例的内存占用情况.
列 | 解释 |
---|---|
Instance | 该类的实例 |
Depth | 深度, 从任一GC Root点到该实例的最短跳数 |
Dominating Size | 该实例可支配的内存大小 |
2.2.3 Reference Tree
图中标③的View.
根据在Instance View中选中的实例, 显示其引用关系树.
此View中的列含义与Instance View一致.
2.3 HPROF Analyzer
另外, 在HPROF Viewer的右侧有一个”Analyzer Tasks”的按钮, 点击会进入HPROF Analyzer的hprof的分析界面:
分析任务包括:
检测泄露的Activity
查找重复的String实例
点击开始按钮后, 会在Analysis Results区域显示分析结果.
HPROF Viewer & Analyzer 可以用来对App的运行中的Java Heap做一个整体分析, 展示当前内存的具体到类和实例的分配情况, 以便检测到可能的内存泄露和重复实例.
3, Allocation Tracker
HPROF Viewer & Analyzer是整体的, 那么Allocation Tracker则是针对操作的分析.
Allocation Tracker可以协助我们分析在一个特定操作时, 有哪些对象被分配内存了. 这可以很方便的让我们知道方法调用的情况, 以便针对性的优化, 以提升性能和内存使用.
在Android Studio的Memory Monitor中点击”Start Allocation Tracking”, 在device中执行一个要分析的操作, 然后再次点击. 如下所示:
可以按照两种方式展示:
Group by Method – 按照线程方法分组显示
Group by Allocator – 按照包分组显示
Method视图中的列含义如下:
列 | 解释 |
---|---|
Method | 方法 |
Count | 该方法分配的实例总数 |
Size | 该方法分配的内存总量(byte) |
可以根据Count和Size分别排序, 找出产生实例多, 耗费内存多的方法, 结合代码分析, 以提升其性能.
4, MAT
Eclipse MAT是一个快速且功能丰富的Java Heap分析工具, 可以帮助我们寻找内存泄露, 减少内存消耗.
MAT可以分析程序(成千上万的对象产生过程中)生成的Heap dumps文件, 它会快速计算出对象的Retained Size, 来展示是哪些对象没有被GC, 自动生成内存泄露疑点的报告.
5, LeakCanary
LeakCanary是大名鼎鼎的square出的一款开源的用来做内存泄露检测的工具.
具体植入方式, 请参考LeakCanary README文档, 略过.
App植入LeakCanary之后, 在检测可能的内存泄露后, 会弹出Toast提示:
点击该icon进入Leaks界面, 可以比较清晰的看到内存泄露疑点:
6, adb shell dumpsys
adb shell dumpsys命令, 该命令可以用户输出当前的系统状态信息.
其中就有关于内存的选项:
1 | $ adb shell dumpsys meminfo com.udinic.perfdemo |
输出信息如下:
该命令常用来查看当前进程的的内存使用状态, 是一个总体的预览.
结语
正所谓善其事先利其器, 了解了内存分析工具的使用, 我们才能更好的分析内存问题, 从而得出解决方案或是明白从哪些方面去避免内存问题.