今天楼主遇到引用LeakCanary时代码跟官网一样但是就不弹出来。楼主新建项目就可以正常使用。楼主郁闷半天,现在终于整出来了。

楼主主工程app引用module为thirdParty,本想为了整洁三方的都扔进这个thirdParty 结果导致了这个没弄出来。

1.写一个application :

[java] view plaincopy print?
  1. <application
  2. android:name=".BaseApplication"
[java] view plaincopy print?
  1. public class BaseApplication extends Application {
  2. private static BaseApplication app;
  3. private DaoMaster daoMaster;
  4. private DaoSession daoSession;
  5. private SQLiteDatabase db;
  6. private String TAG="BaseApplication";
  7. @Override
  8. public void onCreate() {
  9. super.onCreate();
  10. Log.i(TAG, "onCreate: ");
  11. app = this;
  12. LeakCanary.install(this);
  13. initDB();
  14. }

2.写一段让程序泄露的代码:

[java] view plaincopy print?
  1. void startAsyncTask() {
  2. // This async task is an anonymous class and therefore has a hidden reference to the outer
  3. // class MainActivity. If the activity gets destroyed before the task finishes (e.g. rotation),
  4. // the activity instance will leak.
  5. new AsyncTask<Void, Void, Void>() {
  6. @Override
  7. protected Void doInBackground(Void... params) {
  8. // Do some slow work in background
  9. SystemClock.sleep(200000);
  10. return null;
  11. }
  12. }.execute();
  13. Toast.makeText(this, "请关闭这个A完成泄露", Toast.LENGTH_SHORT).show();
  14. }

3.添加build.gradle 由于我把所有的依赖都写在的thirdParty这个lib中

仔细观察一下这个引用不太一样:

我们平时引用都是:

[java] view plaincopy print?
  1. compile 'com.github.lzyzsd.randomcolor:library:1.0.0'

而LeakCanary的引用是:

[java] view plaincopy print?
  1. debugCompile 'com.squareup.leakcanary:leakcanary-android:1.3'

后来我又写到了主app中 结果可以使用了。。。

查了一下他们的含义:

Compile

compile是对所有的build type以及favlors都会参与编译并且打包到最终的apk文件中。

Provided

Provided是对所有的build type以及favlors只在编译时使用,类似eclipse中的external-libs,只参与编译,不打包到最终apk。

APK

只会打包到apk文件中,而不参与编译,所以不能再代码中直接调用jar中的类或方法,否则在编译时会报错

Test compile

Test compile 仅仅是针对单元测试代码的编译编译以及最终打包测试apk时有效,而对正常的debug或者release apk包不起作用。

Debug compile

Debug compile 仅仅针对debug模式的编译和最终的debug apk打包。

Release compile

Release compile 仅仅针对Release 模式的编译和最终的Release apk打包。

还不太清楚为啥。。。但是给大家提个醒。

下面转一个非常好的文章:http://droidyue.com/blog/2016/03/28/android-leakcanary/

懒人可以看我下面的转载

Android内存泄漏检测利器:LeakCanary

MAR 28TH, 2016

是什么?

一言以蔽之:LeakCanary是一个傻瓜化并且可视化的内存泄露分析工具

为什么需要LeakCanary?

因为它简单,易于发现问题,人人可参与。

  • 简单:只需设置一段代码即可,打开应用运行一下就能够发现内存泄露。而MAT分析需要Heap Dump,获取文件,手动分析等多个步骤。
  • 易于发现问题:在手机端即可查看问题即引用关系,而MAT则需要你分析,找到Path To GC Roots等关系。
  • 人人可参与:开发人员,测试测试,产品经理基本上只要会用App就有可能发现问题。而传统的MAT方式,只有部分开发者才有精力和能力实施。

如何集成

尽量在app下的build.gradle中加入以下依赖

1
2
3
4
5
 dependencies {
   debugCompile 'com.squareup.leakcanary:leakcanary-android:1.3.1' // or 1.4-beta1
   releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.3.1' // or 1.4-beta1
   testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.3.1' // or 1.4-beta1
 }

在Application中加入类似如下的代码

1
2
3
4
5
6
7 
public class ExampleApplication extends Application {   @Override public void onCreate() {  super.onCreate();  LeakCanary.install(this);  } } 

到这里你就可以检测到Activity的内容泄露了。其实现原理是设置Application的ActivityLifecycleCallbacks方法监控所有Activity的生命周期回调。内部实现代码为

1
2
3
4
5
6
7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 
public final class ActivityRefWatcher {  private final ActivityLifecycleCallbacks lifecycleCallbacks = new ActivityLifecycleCallbacks() {  public void onActivityCreated(Activity activity, Bundle savedInstanceState) {  }   public void onActivityStarted(Activity activity) {  }   public void onActivityResumed(Activity activity) {  }   public void onActivityPaused(Activity activity) {  }   public void onActivityStopped(Activity activity) {  }   public void onActivitySaveInstanceState(Activity activity, Bundle outState) {  }   public void onActivityDestroyed(Activity activity) {  ActivityRefWatcher.this.onActivityDestroyed(activity);  }  };  private final Application application;  private final RefWatcher refWatcher;   public static void installOnIcsPlus(Application application, RefWatcher refWatcher) {  if(VERSION.SDK_INT >= 14) {  ActivityRefWatcher activityRefWatcher = new ActivityRefWatcher(application, refWatcher);  activityRefWatcher.watchActivities();  }  } .... } 

想要检测更多?

首先我们需要获得一个RefWatcher,用来后续监控可能发生泄漏的对象

1
2
3
4
5
6
7 8 9 10 11 12 13 14 
public class MyApplication extends Application {  private static RefWatcher sRefWatcher;    @Override  public void onCreate() {  super.onCreate();  sRefWatcher = LeakCanary.install(this);  }   public static RefWatcher getRefWatcher() {  return sRefWatcher;  } } 

监控某个可能存在内存泄露的对象

1
MyApplication.getRefWatcher().watch(sLeaky); 

哪些需要进行监控

默认情况下,是对Activity进行了检测。另一个需要监控的重要对象就是Fragment实例。因为它和Activity实例一样可能持有大量的视图以及视图需要的资源(比如Bitmap)即在Fragment onDestroy方法中加入如下实现

1
2
3
4
5
6
7 
public class MainFragment extends Fragment {  @Override  public void onDestroy() {  super.onDestroy();  MyApplication.getRefWatcher().watch(this);  } } 

其他也可以监控的对象

  • BroadcastReceiver
  • Service
  • 其他有生命周期的对象
  • 直接间接持有大内存占用的对象(即Retained Heap值比较大的对象)

何时进行监控

首先,我们需要明确什么是内存泄露,简而言之,某个对象在该释放的时候由于被其他对象持有没有被释放,因而造成了内存泄露。

因此,我们监控也需要设置在对象(很快)被释放的时候,如Activity和Fragment的onDestroy方法。

一个错误示例,比如监控一个Activity,放在onCreate就会大错特错了,那么你每次都会收到Activity的泄露通知。

如何解决

常用的解决方法思路如下

  • 尽量使用Application的Context而不是Activity的
  • 使用弱引用或者软引用
  • 手动设置null,解除引用关系
  • 将内部类设置为static,不隐式持有外部的实例
  • 注册与反注册成对出现,在对象合适的生命周期进行反注册操作。
  • 如果没有修改的权限,比如系统或者第三方SDK,可以使用反射进行解决持有关系

加入例外

有些特殊情况,我们需要忽略一些问题,这时候就需要添加例外规则。比如ExampleClass.exampleField会导致内存泄漏,我们想要忽略,如下操作即可。

1
2
3
4
5
6
7 8 9 
// ExampleApplication is defined in "Customizing and using the no-op dependency"
public class DebugExampleApplication extends ExampleApplication {  protected RefWatcher installLeakCanary() {  ExcludedRefs excludedRefs = AndroidExcludedRefs.createAppDefaults()  .instanceField("com.example.ExampleClass", "exampleField")  .build();  return LeakCanary.install(this, DisplayLeakService.class, excludedRefs);  } } 

如何实现的

LeakCanary实际上就是在本机上自动做了Heap dump,然后对生成的hprof文件分析,进行结果展示。和手工进行MAT分析步骤基本一致。

如何不影响对外版APK

是的,这个问题确实值得关注,因为LeakCanary确实是影响程序运行的,尤其是heap dump操作,不过好在这件事Square已经考虑了,即在我们增加依赖时

1
2
3
debugCompile 'com.squareup.leakcanary:leakcanary-android:1.3.1' // or 1.4-beta1 releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.3.1' // or 1.4-beta1 testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.3.1' // or 1.4-beta1 

其中releaseCompile和testCompile这两个的依赖明显不同于debugCompile的依赖。它们的依赖属于NOOP操作。

NOOP,即No Operation Performed,无操作指令。常用的编译器技术会检测无操作指令并出于优化的目的将无操作指令剔除。

因而,只要配置好releaseCompile和testCompile的依赖,就无需担心对外版本的性能问题了。

实践中的问题

  • 如果targetSdkVersion为23,在6.0的机器上会存在问题,卡死,因为LeakCanary并没有很好支持Marshmallow运行时权限,所以始终得不到sd卡权限,进而导致卡死。

注意

  • 目前LeakCanary一次只能报一个泄漏问题,如果存在内存泄漏但不是你的模块,并不能说明这个模块没有问题。建议建议将非本模块的泄漏解决之后,再进行检测。

Anroid中内存泄漏相关文章

  • 避免Android中Context引起的内存泄露
  • Android中Handler引起的内存泄露
  • Google为何这样设计OnSharedPreferenceChangeListener
  • Google IO:Android内存管理主题演讲记录
  • 译文:理解Java中的弱引用
  • 细话Java:”失效”的private修饰符

使用LeakCanary遇到的问题 就是不弹出来相关推荐

  1. LeakCanary——直白的展现Android中的内存泄露

    之前碰到的OOM问题,终于很直白的呈现在我的眼前:我尝试了MAT,但是发现不怎么会用.直到今天终于发现了这个新工具: 当我们的App中存在内存泄露时会在通知栏弹出通知: 当点击该通知时,会跳转到具体的 ...

  2. leakcanary内存泄露检测工具 Dumping memory, app will freeze. Brrr

    官网地址 https://github.com/square/leakcanary 官网继承步骤就2步,超简单,但是集成进项目后, 问题一:一直弹出("Dumping memory, app ...

  3. 一步步拆解 LeakCanary

    本篇文章已授权微信公众号 guolin_blog (郭霖)独家发布 java 源码系列 - 带你读懂 Reference 和 ReferenceQueue https://blog.csdn.net/ ...

  4. LeakCanary是如何定位内存泄漏的,看完就懂了

    文章目录 一.LeakCanary的简单使用 二.LeakCanary原理简单分析: 2-1.LeakCanary原理简述 2-2.ActivityLifecycleCallbacks使用 2-2-1 ...

  5. leakCanary原理

    一.面试中的问题 一般的中高级面试,都会问到性能优化,内存优化问题,而说到内存问题就肯定会问到内存泄漏问题,而一般的求职者二话不说,直接就上LeakCanary, 紧接着肯定是问:那你知道LeakCa ...

  6. android leakcanary 源码分析,LeakCanary源码浅析

    在Android开发中最让人们头疼的就是内存泄漏了,今天来介绍一个查看内存是否泄漏的工具LeakCanary,并通过研究源码明白它是如何分析和查找存在泄漏信息的 在Android开发中最让人们头疼的就 ...

  7. Android内存泄漏分析及检测工具LeakCanary简介,androidui库

    Android内存优化是APP稳定运行的重要一环,开发过程中如果代码写的过于随意,很容易造成内存泄漏,多次累积之后,便会产生OOM,进而造成app崩溃.本文介绍了内存泄漏的相关知识和检测工具LeakC ...

  8. Android 内存泄漏检测开源库LeakCanary 研究

    1. Android 内存空间不足会引发的问题 1.1 异常 1.2 卡顿 1.3 从 Java 堆内存超限这个问题开始 2. 内存优化着手点 2.1 检测 RAM usage 2.2 进程 2.3 ...

  9. Android性能优化之利用强大的LeakCanary检测内存泄漏及解决办法

    本篇文章主要介绍了Android性能优化之利用LeakCanary检测内存泄漏及解决办法,有兴趣的同学可以了解一下. 目录 前言 什么是内存泄漏? 内存泄漏造成什么影响? 什么是LeakCanary? ...

最新文章

  1. SQLite基本操作
  2. ASCII码表完整版
  3. free网页服务器,Web网站服务(一)
  4. LOAD DATA INFILE 语法
  5. win10怎么设置默认输入法_win10系统输入法失效打不了字怎么办
  6. webpack实用配置
  7. java 学习笔记_java学习笔记
  8. PingInfoView,中文,以及ping包+描述的使用。
  9. 液压减振器 matlab,摩托车液压减振器内泄漏对阻尼力影响计算及其对策
  10. [201209][HTTP 权威指南][陈涓][赵振平][译]
  11. matlab linux命令行窗口,linux命令行运行matlab
  12. imx6 linux内核定义debug口,IMX6Q 调试串口修改
  13. Matlab中滤波操作的相关函数
  14. vmd python 命令_【MMD】用python解析VMD格式读取
  15. 常见的各种人提出的理论
  16. steam版拳皇14无法正常启动
  17. 学汽修和计算机对比,学计算机和汽车维修哪个好
  18. dvi是什么意思_VGA线和DVI线,VGA线和DVI线是什么意思
  19. sql server作业实现数据同步
  20. 地形建模(一)——TIN地形的生成

热门文章

  1. jvm:虚方法与非虚方法
  2. javaweb:servlet
  3. 数据结构: 排序算法介绍
  4. linux系统管理命令,压缩命令
  5. java七大设计原则
  6. 前端之javaScript
  7. 常见Oracle HINT的用法
  8. 通过命令删除在ambari界面上无法删除节点上服务
  9. [javaSE] java获取文件列表
  10. 判断字符串1是否在字符串2中出现的方法