美文网首页
51.LeakCanary分析

51.LeakCanary分析

作者: 任振铭 | 来源:发表于2021-08-04 08:35 被阅读0次

    使用

    debugCompile 'com.squareup.leakcanary:leakcanary-android:1.3'
    releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.3'
    
    public class MyApplication extends Application {
          @Override
          public void onCreate() {
                 super.onCreate();
                 LeakCanary.install(this)
          }
    }
    

    源码

    1.LeakCanary是怎么做到install之后自动监测Activity的?

    调用install后,会注册一个Activity生命周期的回调监听,registerActivityLifecycleCallbacks,来绑定Activity生命周期,在Activity执行onDestroy时,调用watch方法开始检测当前页面是否存在内存泄漏,并分析结果(如果想要在非Activity如Fragment检测是否存在内存泄漏,需要手动添加,调用watch方法)

    2.如何判定Activity是否发生了内存泄漏

    KeyedWeakReference与ReferenceQueue联合使用,将onDestroy的Activity对象包裹成一个弱引用对象(KeyedWeakReference),开启异步线程,在弱引用关联的对象被回收后,会将引用添加到ReferenceQueue;清空后,可以根据是否继续含有该引用来判定是否被回收;判定回收, 手动GC, 再次判定回收,采用双重判定来确保当前引用是否被回收的状态正确性;如果两次都未回收,则确定为泄漏对象。

    3.内存泄漏轨迹是如何生成的

    采用eclipse.Mat来分析泄漏详细,从GCRoot开始逐步生成引用轨迹。

    4.内存分析是在单独的进程执行的吗,为什么?

    内存分析模块是在独立进程中执行的,这么设计是为了保证内存分析过程不会对App进程造成消极的影响

    5.检测是否发生泄漏是在主线程还是子线程

    开启了一个子线程检测的

    5.Leak Canary核心类及其作用

    1.DisplayLeakActivity
    内存泄漏的查看页面
    2.HeapAnalyzerService
    内存堆分析服务, 为了保证App进程不会因此受影响变慢&内存溢出,运行于独立的进程
    3.HeapAnalyzer
    分析由RefWatcher生成的堆转储信息, 验证内存泄漏是否真实存在
    4.HeapDump
    堆转储信息类,存储堆转储的相关信息
    5.ServiceHeapDumpListener
    一个监听,包含了开启分析的方法
    6.RefWatcher
    核心类, 翻译自官方: 检测不可达引用(可能地),当发现不可达引用时,它会触发
    7.HeapDumper
    (堆信息转储)
    8.ActivityRefWatcher
    Activity引用检测, 包含了Activity生命周期的监听执行与停止

    6.LeakCanary检测内存泄漏的原理

    LeakCanary在Application中install既初始化之后,通过ApplicationContext统一注册监听的方式(application.registerActivityLifecycleCallbacks),来观察所有的Activity的生命周期,在Activity执行onDestroy的时候通过RefWatcher执行watch方法来检测本页面是否存在内存泄漏的问题(watch传入的参数是activity引用,如果我们想单独监听某块代码,如fragment或View等,我们需要手动去调用watch()来检测;因为默认的watch()仅执行于Activity的Destroy时),watch方法会创建一个 KeyedWeakReference(key value的形式保存activity引用,防止在多个相同Activity实例存在的时候无法判断是哪个activity) 来包装要被监控的对象。然后根据检测引用是否被清除(如何判断引用是否被清除?被弱引用包裹的actvity如果被回收,就会把这个弱引用加入到引用队列,如果队列中存在这个activity的弱引用,那么就说明activity被回收),如果当前引用不存在了,说明没有泄漏发生,不再执行。如果当前引用仍然存在,则手动触发一次gc操作,然后再次检测引用是否被清除,如果是,说明没有泄漏发生,如果仍然存在,则说明发生了内存泄漏,生成文件,保存内存分析信息 。

    相关文章

      网友评论

          本文标题:51.LeakCanary分析

          本文链接:https://www.haomeiwen.com/subject/hagyvltx.html