ThreadLocal 引起的内存泄露
解决方案
线程未取消引用的内存泄露
1,viewpager自动滚动+手动滚动 线程没有正确关闭
解决方案
如果不为空先停线程,再开启新线程
静态变量,单例,或长生命周期集合 直接或间接持有短生命周期引用(如:context,view,)相关的引用, 引起的内存泄露 (第三方sdk接收context后用静态变量持有引用)
解决方案
在 Activity 回调 onDestroy 时或者 onStop 时 静态变量置null 或 使用Context时,尽量使用Application 的 Context,或 移除引用
handler引起的
一,子消息循环 handlerThread + looper
解决方案
停线程
二 ,handler post 方式内存泄露 ,移除消息队列 MessageQueue 中的消息
解决方案
mHandler.removeCallbacksAndMessages(null)
匿名内部类持有外部类,该匿名内部类被保存到一个生命周期> 外部类的容器中的情况。
解决方案
将非静态内部类转为静态内部类 + WeakReference(弱引用)的方式
WebView引起的内存泄露
解决方案
WebView在加载页面时,会长期占用内存而不能被释放,因为WebView的网络请求由内核实现,所以app端无法对其进行控制。
同大多数操作一样,在Activity销毁时调用WebView#destroy()。
在Android 5.1版本以后,WebView中添加的Callback会持有Activity的引用,从而造成即使调用了destroy()方法,也无法释放WebView占用的内存。
在销毁WebView之前,先把WebView从其父容器之中移除
https://blog.csdn.net/xygy8860/article/details/53334476
资源未关闭
解决方案
Bitmap 使用后调用recycle()方法
io流,file 用正常的方式close
未反注册
如:在Activity中动态注册广播监听,如果在Activity销毁时未进行unregister,那么这么广播会一直存在于系统中,并且持有Activity的引用,从而造成内存泄露。
解决方案
用正确的方式反注册
系统键盘引起的
解决方案
重载Finalize引发让对象起死回生
解决方案
https://zhuanlan.zhihu.com/p/27850176
LeakCanary原理分析
在一个Activity执行完onDestroy()之后,将它放入
WeakReference中,然后将这个WeakReference类型的Activity对象
与ReferenceQueque关联。这时再从ReferenceQueque中查看是否
有没有该对象,如果没有,执行gc,再次查看,还是没有的话则判
断发生内存泄露了。最后用HAHA这个开源库去分析dump之后的
heap内存。
网友评论