博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
【转】LeakCanary
阅读量:4880 次
发布时间:2019-06-11

本文共 2116 字,大约阅读时间需要 7 分钟。

LeakCanary:检测所有的内存泄漏

http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2015/0509/2854.html

原文:  

1
2
3
4
ava.lang.OutOfMemoryError
        
at android.graphics.Bitmap.nativeCreate(Bitmap.java:-2)
        
at android.graphics.Bitmap.createBitmap(Bitmap.java:689)
        
at com.squareup.ui.SignView.createSignatureBitmap(SignView.java:121)

没人喜欢OutOfMemoryError

在Square的注册过程中,我们在bitmap上 。这个bitmap和设备的屏幕大小相当,在创建它的时候,我遇到了相当数量的OOM导致的崩溃。

signature.png

我们试过了几种方法,没有一个解决了我们的问题:

  • 使用Bitmap.Config.ALPHA_8(签名是不需要颜色的)

  • 捕获OutOfMemoryError,触发垃圾回收然后重试几次(从 获得的启发)

  • 我们没有考虑过将bitmap分配在堆内存之外,那个时候 还没出现。

我们看待问题的方式是不对的

bitmap的大小本身不是什么问题。当内存快要满了的时候,OOM随时随地都可能发生。尤其是在创建大对象的时候更容易发生,比如bitmap。OOM一般代表着更深层次的问题:内存泄漏

什么是内存泄漏?

有些对象只有有限的生命周期。当它们的任务完成之后,它们将被垃圾回收。如果在对象的生命周期本该结束的时候,这个对象还被一系列的引用,这就会导致内存泄漏。随着泄漏的累积,app将消耗完内存。

比如,在Activity.onDestroy()被调用之后,view树以及相关的bitmap都应该被垃圾回收。如果一个正在运行的后台线程继续持有这个Activity的引用,那么相关的内存将不会被回收,这最终将导致OutOfMemoryError崩溃。

寻找内存泄漏

寻找内存泄漏是一个人工操作的过程,在Raizlabs的  系列中描述得很清楚。

下面是关键的步骤:

  1. 通过 , , 或者 了解OOM

  2. 主动重现问题。你可能需要买或者借或者偷一个遭遇了崩溃的特殊设备(并不是所有的设备上都会发生内存泄漏!)。你还需要找出是什么串在一起导致了内存泄漏。

  3. 当OOM出现时进行堆转储(dump the heap)().

  4. 使用MAT或YourKit内存检测工具检测内存的变化,并找出哪个对象应该被垃圾回收;

  5. 从那个对象到GC roots推断最短的强引用路径;

  6. 在路径中找出不存在的引用,并修复memory leak;

要是有一个库可以为你做完所有的事情,让你专注于修复内存泄漏的问题,那该有多好。

LeakCanary介绍

 是一个开源的在debug版本中检测内存泄漏的java库。

让我们来看看一个cait的例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
class Cat {
}
class Box {
  
Cat hiddenCat;
}
class Docker {
  
static Box container;
}
 
// ...
 
Box box = 
new 
Box();
Cat schrodingerCat = 
new 
Cat();
box.hiddenCat = schrodingerCat;
Docker.container = box;

创建一个RefWatcher实例,然后给它一个对象让它观察:

1
2
// We expect schrodingerCat to be gone soon (or not), let's watch it.
refWatcher.watch(schrodingerCat);

当检测出泄漏的时候,你会自动得到一个漂亮的泄漏线索:

1
2
3
* GC ROOT static Docker.container
* references Box.hiddenCat
* leaks Cat instance

我们知道你的时间宝贵,因此我们让它非常好设置。只需几行代码,LeakCanary就能自动检测Activity的泄漏:

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

当内存不足时,会有一个通知和良好的展示界面:

leaktrace.png

结论

在启用LeakCanary之后,我们发现和修复了许多内存泄漏的问题。我们甚至发现了一些。

结果是非常令人惊奇的,我们现在减少了94%的oom崩溃问题。

oom_rate.png

如果你想终结OOM崩溃,!

转载于:https://www.cnblogs.com/kiwihere/p/4885543.html

你可能感兴趣的文章
找不到可安装的ISAM ,asp.net读取数据丢失,解决的一列里有字符与数字的
查看>>
Java学习笔记三(对象的基本思想一)
查看>>
Java程序(文件操作)
查看>>
KMP算法 最小循环节 最大重复次数
查看>>
Proving Equivalences (强连通,缩点)
查看>>
Period (KMP算法 最小循环节 最大重复次数)
查看>>
sgu 103. Traffic Lights
查看>>
poj 3621 Sightseeing Cows
查看>>
hdu 3666 THE MATRIX PROBLEM
查看>>
TopCoder SRM 176 Deranged
查看>>
Javascript中数组与字典(即map)的使用
查看>>
C++不完整的类型
查看>>
memcached(十三)注意事项
查看>>
ITerms2在mac系统下的安装和配色,并和go2shell关联
查看>>
nginx常见面试题1
查看>>
小白用shiro(1)
查看>>
微服务化之无状态化与容器化
查看>>
动态规划LeetCode174地下城游戏
查看>>
Sublime Text 报“Pylinter could not automatically determined the path to lint.py
查看>>
自动化测试用例getText()获取某一个元素的值返回null或空
查看>>