static关键字所导致的内存泄漏问题
Posted 皇问天
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了static关键字所导致的内存泄漏问题相关的知识,希望对你有一定的参考价值。
大家都知道内存泄漏和内存溢出是不一样的,内存泄漏所导致的越来越多的内存得不到回收的失手,最终就有可能导致内存溢出,下面说一下使用staitc属性所导致的内存泄漏的问题。
在dalvik虚拟机中,static变量所指向的内存引用,如果不把它设置为null,GC是永远不会回收这个对象的,所以就有了以下情况:
- public class SecondActivity extends Activity{
- private Handler mHandler = new Handler(){
- @Override
- public void handleMessage(Message msg) {
- super.handleMessage(msg);
- SecondActivity.this.finish();
- this.removeMessages(0);
- }
- };
- private static Haha haha;
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- haha = new Haha();
- mHandler.sendEmptyMessageDelayed(0,2000);
- }
- class Haha{
- }
- }
非静态内部类的静态引用。然后在2秒之后我们要finish掉这个activity,会造成什么问题呢?我们知道,内部类和外部类之间是相互持有引用的,SecondActivity实例持有了haha的引用,但这里haha是用static修饰的,上面说了,虚拟机不会回收haha这个对象,从而导致SecondActivity实例也得不到回收,造成内存溢出。
这货还在这得不到回收。
怎么解决这个问题呢,很简单,只要在Activity的onDestroy方法里把haha设为null就行啦
- protected void onDestroy() {
- super.onDestroy();
- if(haha!=null){
- haha = null;
- }
- }
那么还有另外一种情况,单例的问题。单例也是用了其static属性,很多单例,往往需要用到context对象,而又是通过传值的方式获得,比如:
先来一个单例
- public class SingleInstanceF {
- private static SingleInstanceF single;
- private Context context;
- private SingleInstanceF(Context context){
- this.context = context;
- }
- public static SingleInstanceF getInstance(Context context){
- if(single==null){
- single = new SingleInstanceF(context);
- }
- return single;
- }
- }
再来一个Activity来用它,context传入一个this,再2秒之后关闭Activity
- public class ThirdActivity extends Activity{
- private Handler mHandler = new Handler(){
- @Override
- public void handleMessage(Message msg) {
- super.handleMessage(msg);
- ThirdActivity.this.finish();
- this.removeMessages(0);
- }
- };
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- SingleInstanceF instanceF = SingleInstanceF.getInstance(this);
- mHandler.sendEmptyMessageDelayed(0,2000);
- }
- }
后来我们发现这货还在,又是得不到回收:
怎么办呢,还是像上面那样,把静态对象设置为null,或者我们传入context的时候,别传this了,this可是当前Acitvity啊,传Application Context即可。但是不是都可以传Application Context呢,明显不是,有的事是Application Context干不了的,这个得看具体情况而定。
以上是关于static关键字所导致的内存泄漏问题的主要内容,如果未能解决你的问题,请参考以下文章
Android面试每日一题: 一般什么情况下会导致内存泄漏问题?