Android 内存泄露(Memory Profiler和LeakCanary)

什么是内存泄露?
按照传统定义,内存泄露属于对象,正在运行的程序无法访问这个对象,但这个对象仍然占据
着内存这就叫内存泄露。这在c/c++里面的指针比较好理解。

但是在kotlin和java中情况有些不同,因为这些程序是在Java虚拟机(JVM)里面运行的,在JVM中“垃圾回收(GC)”是个重要概念,虚拟机会在GC时首先确认GC Root,GC Root是一种对象,可以从堆外访问,如本地变量,运行线程等,随后,虚拟机会辨别所有可以通过GC Root访问的对象,它们将会保留。无法通过GC Root访问的变量会被当做垃圾回收。

因此传统定义的内存泄露在JVM中并不存在。那么我们提到JVM中内存泄露的时候指的又是什么呢?
我们所指的一般是被放弃的对象,程序将永不再次使用它,但它仍然是可以访问的。
在Android 中有两种对象是绝对不可以泄露的,Fragment和Activity,因为这两者通常会占用大量的内存。

Android Studio 3.6以后Memory Profiler可以自动检测Fragment和Activity的泄露,就是抓取Heap Dump文件。

Memory Profiler是怎么发现内存泄露的呢?
Activity如果销毁了,那么我们知道程序不会再使用它了,如果它再被引用就表示泄露了。
Fragment必须与FragmentManager搭配才可用,如果发现Fragment没有和FragmentManager一起出现,这时如果它被引用就表示泄露了。但是要注意如果你正好在Fragment被创建后但被使用前的某个点Heap Dump,Memory Profiler会报一个错误的诊断结果,如果Fragment被缓存但仍未被复用也是一样。

在这里插入图片描述
Shallow Size:对象本身消耗内存
Native Size:本地对象的尺寸
Retained Size:保留尺寸
Depth:深度是从GC Root到这个实例的最短距离

在这里插入图片描述
对象距离GC Root越近,它拥有GC Root到这个实例多条路径的可能性就越高,结果是它比较不可能会被当做垃圾回收。
比如红色7,如果左边任意应用被破坏,那么红色7就会变得无法访问,被当做垃圾回收
如果想回收蓝色2,那么就必须打断左边和右边的引用
如果你看到任何深度为1的实例,那么就是很强烈的信号,代表这个实例是直接被GC Root引用的。

在这里插入图片描述
分析Heap Dump
在这里插入图片描述

在这里插入图片描述

写给程序员的内存泄漏治理手册
LeakCanary2.0使用及原理分析 — Kotlin重构版

读懂 Android Studio 分析工具数据 | AndroidDevSummit 中文字幕视频

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

哆啦A梦z

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值