Message Android的享元模式

在Android中,几乎逃不过Handler这个组件,Android作为一个操作系统是基于事件驱动的,每一事件都会转化为系统消息。而事件驱动的几个组件:Message, MessageQueue, Handler, Looper不管怎么样你都绕不过去。每一个APP进程都有一个默认的消息列表,也就是MessageQueue。它们之间的运行原理就像工厂的生产线一样,代加工的商品就是Message,工人对应的就是处理事件的Handler。对于系统来说Message必然会产生很多的对象。在我们使用Handler中 不推荐直接new Message(),显然重复大量创建Message不是Android的实现方式。

我们通过一个简单的例子来看一下,Message的生命周期是怎么样的?

public class Mainactivity extends Activity{
  Handler handler = new Handler(Looper.getMainLooper());
  
  private void dosomeThing(){
    new Thread(){
      public void run(){
            handler.post(new Runnable(){
              public void run(){
                
              }
            }); 
      }
    }
  }
}

在上面的例子我们创建了一个Handler 将一个Runnable传递给UI线程,实际上handler.post会将Runnabel包装成一个Message。我们Message的消息是从obtain()方法中获取到的。

public final boolean post(Runnable r){
  return sendMessageDelayed(getPostMessage(r),0);
}

private static Message getPostMessage(Runnabel r){
  Message m = Message.obtain();
  m.callback = r;
  return m;
}
public static Message obtain(){
  synchronized(sPoolSync){
        if(sPool != null){
          Message m = sPool;
          sPool = m.next;
          m.next = null;
          m.flag = 0;// 清除使用的标记
          sPoolSync--;
        } 
  }
  return new Message();
}

sPool我们从名称大概也能猜到这应该是一个对象池,但是点击发现起始它是一个对象,仔细发现其中包含有一个Message next,不难猜到这个大概是使用了链表的数据结构来构造一个对象池,至此我们已经明白了Message的如何获取的,但是我们没有发现Message是何时存入到链表中的。

一番搜索我们发现了Message 中也有类似Bitmap那样的Recycle函数,来获取Message添加到链表中

public void recycle(){
  //省略
  recycleUnchecked();
}

void recyclerUnchecked(){
  flags = Flag_in_use;
  what = 0;
  arg1 = 0;
  arg2 = 0;
  obj = null;
  replyTo = null;
  when = 0;
  target = null;
  callback = null;
  
  data = null;
  synchronized(sPoolSync){
    if(sPoolSize < MAX_POOL_SIZE){
      next = sPool;
      sPool = this;
      sPoolSize++;
    } 
  }
}

你可能感兴趣的:(Message Android的享元模式)