【Android自助餐】Handler消息机制完全解析(一)Message中obtain()与recycle()的来龙去脉
【Android自助餐】Handler消息机制完全解析(一)Message中obtain()与recycle()的来龙去脉
- Android自助餐Handler消息机制完全解析一Message中obtain与recycle的来龙去脉
- 提供obtain
- 回收recycle
提供obtain()
在obtain的所有重载方法中,第一行都是Message m = obtain();
,即调用空参的方法。
先来看一下这个空参方法
public static Message obtain() { synchronized (sPoolSync) { if (sPool != null) { Message m = sPool; sPool = m.next; m.next = null; m.flags = 0; // clear in-use flag sPoolSize--; return m; } } return new Message();}
很明显,这是个同步方法,sPoolSync
即锁对象,该对象在定义时即被初始化private static final Object sPoolSync = new Object();
,随后便只读不写。
然后便是sPool
,后面还有Message m = sPool;sPool = m.next;
,很明显可以看出来,这是一个链表结构。sPool
指向当前message,next
指向下一个message。
在解释这段代码前,需要先明确两点:sPool
声明为private static Message sPool;
;next
声明为/*package*/ Message next;
。即前者为该类所有示例共享,后者则每个实例都有。
现在为了便于理解,我们将Message
抽象为C语言中的链表节点结构体,指针域便是用于指向下一个消息的next
字段,其他则都视为数据域。
假设该链表初始状态如下
执行Message m = sPool;
就变成下图
继续sPool = m.next;
然后m.next = null;
接下来m.flags=0;sPoolSize--;return m;
便是表示m指向的对象已经从链表中取出并返回了。
回收recycle()
然后再看看sPoolSize
是什么时候自增的。按图索骥便可找到recycle()
方法和recycleUnchecked()
方法。前者供开发者调用进行回收,后者执行回收操作。来看看回收操作都干了啥:
void recycleUnchecked() { // Mark the message as in use while it remains in the recycled object pool. // Clear out all other details. flags = FLAG_IN_USE; what = 0; arg1 = 0; arg2 = 0; obj = null; replyTo = null; sendingUid = -1; when = 0; target = null; callback = null; data = null; synchronized (sPoolSync) { if (sPoolSize < MAX_POOL_SIZE) { next = sPool; sPool = this; sPoolSize++; } }}
前半段不必多说,显然是“重置”改对象的个个字段。后半段又是一个同步代码段,同样用图来解释一下(假设当前代码为message.recycle()
,则需要被回收的则是message
对象)。
假设当前链表如下:
执行next=sPool;
执行sPool=this
;
现在可以很清楚的看到,Message类本身就组织了一个栈结构的缓冲池。并使用obtain()
方法和recycler()
方法来取出和放入。
更多相关文章
- Android 操作系统的内存回收机制
- Android 事件分发机制总结
- 【幻灯片分享】Android消息推送实现 | 友盟 徐仙明 | Android De
- android应用安全——签名机制
- Android事件处理方法总结-Handler消息处理
- 比较详细的handle机制