zoukankan      html  css  js  c++  java
  • 说说内存泄露那点事

    先看看一个例子:

     1 private static Drawable sBackground;
     2 
     3 @Override
     4 protectedvoid onCreate(Bundle state){
     5   super.onCreate(state);
     6   
     7   TextView label =newTextView(this);
     8   label.setText("Leaks are bad");
     9   
    10   if(sBackground ==null){
    11     sBackground = getDrawable(R.drawable.large_bitmap);
    12   }
    13   label.setBackgroundDrawable(sBackground);
    14   
    15   setContentView(label);
    16 }
    17  

    上面几行代码,内存泄露挺严重的。sBackground是一个 static 变量,在 label调用setBackgroundDrawable的时候,会调用sBackground的setCallback,所以在sBackground中就存在label的引用。

    而,label中又存在Activity的引用,所以此Activity一直不会被回收,即使已经finish了。

    如何避免:

    1. 使用applicationContext作为上下文,避免使用activity
    2. 设置Drawable的Callback为null
    3. 在Service或者Activity使用内部类尽量使用static类。例如:使用Handler

     

    关于第3点,看个例子:

     1    static class IncomingHandlerextendsHandler {
     2         private final WeakReference<UDPListenerActivity> mActivity;
     3  
     4         IncomingHandler(UDPListenerActivity activity) {
     5             mService = newWeakReference < UDPListenerActivity > (activity);
     6         }
     7  
     8         @Override
     9         public void handleMessage(Message msg) {
    10             UDPListenerActivity activity = mActivity.get();
    11             if (activity != null) {
    12                 activity.handleMessage(msg);
    13             }
    14         }
    15    } 
    我们知道,Message发出之后是存在MessageQueue中的,有些Message也不是马上就被处理的。在Message存在一个 target,是Handler的一个引用,如果Message在Queue中存在的时间越长,就会导致Handler无法被回收。如果Handler是非静态的,则会导致Activity或者Service不会被回收。
    所以正确处理Handler等之类的内部类,应该采用上述代码。

     

    参考:
     
     
    -----END-----
  • 相关阅读:
    802.11帧
    art中的部分内容,留着慢慢研究
    802.11基础知识
    opkg
    openwrt生成备份文件
    lua中获取时间
    php学习四:数组(一)
    php学习三:函数
    php学习二:表达式
    php学习一:语法规则
  • 原文地址:https://www.cnblogs.com/halzhang/p/3069609.html
Copyright © 2011-2022 走看看