The application of the interview handle and its principles (1)

How Message is created

If you are asked in an interview how many ways can messages be created?

  1. Message MSG = New Message() : creates a Message object

  2. myHander.obtainMessage(); : myHandler is of the Handler type

To create a Message, use this method directly. Check out the source code

    public final Message obtainMessage()
    {
        return Message.obtain(this);
    }
Copy the code

It calls the third Message creation method we’ll mention

  1. Message.obtain():
public static Message obtain(Handler h) {
        Message m = obtain();
        m.target = h;

        return m;
    }

   public static Message obtain() {
        synchronized (sPoolSync) {
            if(sPool ! = null) { Message m = sPool; sPool = m.next; m.next = null; m.flags = 0; // clearin-use flag
                sPoolSize--;
                returnm; }}return new Message();
    }
Copy the code

The obtain() source code above uses a linked list structure to store Messages as a cache pool, which avoids creating multiple implementation objects repeatedly.

The second creation method simply calls the third object that fetched Message from the cache pool and assigns Handler to message.target. All three of these are ways to create a Message

Message cache pool correlation

Message data structure

public final class Message implements Parcelable {
        ......
    /*package*/ Message next;
}
Copy the code

This is obviously a linked list structure, so let’s look at it

public static Message obtain() {
        synchronized (sPoolSync) {
            if(sPool ! = null) { Message m = sPool; sPool = m.next; m.next = null; m.flags = 0; // clearin-use flag
                sPoolSize--;
                returnm; }}return new Message();
    }
Copy the code

If sPool’s single list of messages is not null, retrieve the Message in the list header and reset sPool. The sPoolSize is reduced by one. If sPool is null, a new Message object is returned

Take a look at the method used to add a Message to sPool

    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++; }}}Copy the code

Clear some variable information, then determine if the list does not exceed the maximum value, add it to the header and increase the list size by one

    private static final int MAX_POOL_SIZE = 50;
Copy the code

The maximum value of a linked list is 50

For objects that are frequently created, it is best to add a buffer pool to retrieve objects that have already been created. Instead of just creating it every time.