Original address:
http://blog.csdn.net/xplee0576/article/details/46875555
In Android, we usually use Android's messaging mechanism for communication between threads, and this mechanism passes exactly the message.
In general, we use message.obtain() and handler.obtainmessage () to get a message from the message pool to avoid constructing the message directly.
- so does Android cause oom because the message pool caches the message object? for this question, I can clearly say that the app will not be oom because of the message pool. As for why, can take a step-by-step look down, impatient can directly see the last section--message pool how to store a Message.
Message Obtain analysis: message.obtain () source code:
/** * Return a new Message instance from the Glo Bal pool. Allows us to * avoid allocating new objects in many cases. */public static Message obtain () { Span class= "Hljs-keyword" >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 ();
From the code slice, you can see that the message is assigned directly by spool.
handler.obtainmessage () Source code
/** * Returns a new {@link android.os.Message Message} from the global message pool. More efficient than * creating and allocating new instances. The retrieved message has its handler set to this instance (Message.target == this). * If you don‘t want that facility, just call Message.obtain() instead. */ public final Message obtainMessage() { return Message.obtain(this); }
Handler.obtain () is eventually called Message.obtain () to get it.
Message Pool related source code AnalysisMessage Pool Data structure
Sometimes we store linked lists of these things/*package*/Message next; private static final Object Spoolsync = new Object (); private static Message SPool; private static int sPoolSize = Span class= "Hljs-number" >0; private static final int max_pool_size = 50; private static boolean Gcheckrecycle = true;
It is clear from the code that the data structure of the Message pool is actually a linked list. Spool is a global message pool, Spoolsize records the length of the linked list, max_pool_size indicates that the maximum length of the list is 50.
message Pool How to store message
/**@hide */PublicStaticvoidUpdatecheckrecycle (int targetsdkversion) {if (Targetsdkversion < build.version_codes. LOLLIPOP) {gcheckrecycle =False } }/** * Return A Message instance to the global pool. * <p> * You must don't touch the Message after calling this function because it has * effectively been freed. It's an error to recycle a message that's currently * enqueued or that's in the process of being delivered to a Handler . * </p> * *PublicvoidRecycle () {if (Isinuse ()) {if (gcheckrecycle) {ThrowNew IllegalStateException ("This message cannot is recycled because it" +"is still on use."); }Return } recycleunchecked (); }/** * Recycles a Message that is May in-use. * Used internally by the MessageQueue and Looper when disposing of queued Messages. */void recycleunchecked () {//Mark the message as in use while it REM Ains in the Recycled object pool. //Clear out all the details. Flags = flag_in_use; what = 0; arg1 = 0; arg2 = 0; obj = null; replyTo = null; Sendinguid =-1; when = 0; target = null; data = null; synchronized (spoolsync) {if (Spoolsize < MAX_POOL_SIZE) { Next = SPool; SPool = this; spoolsize++;}} }
From the code analysis, the core method of message pool storage is the recycleunchecked () method above:
1. Empty the Message object field to be reclaimed (avoid a static message pool memory leak due to the message being too large). therefore, regardless of how large the original message object is, and is eventually cached before the message pool is empty, the memory size of these cached message objects is basically negligible for an app memory. Therefore, the Message pool does not cause the app to Oom.
2, in the way of built-in lock (thread safety), determine whether the current thread pool size is less than 50. If it is less than 50, the mesaage is inserted directly to the tail of the message pool chain, and if it is greater than or equal to 50, the discarded message is disposed of by GC.
What is the message pool for Android-Source perspective analysis