7

在线程、视图或活动之间发送消息时,有两种看似相同的方法。

第一个,对我来说最直观的,是obtaina Message,然后使用Handler'ssendMessage方法:

Message msgNextLevel = Message.obtain();
msgNextLevel.what = m.what;
mParentHandler.sendMessage(msgNextLevel);

或者,您可以obtain提供消息Handler,然后使用Message'sendToTarget方法:

Message msg = Message.obtain(parentHandler);
msg.what = 'foo';
msg.sendToTarget();

为什么存在这两种实现同一目标的方法?他们的行为是否不同?

4

2 回答 2

6

例如,如果您从此处检查 Message.java 代码,您将看到

//Sends this Message to the Handler specified by getTarget().


public void sendToTarget() {
    target.sendMessage(this);
}

换句话说,sendToTarget()将使用先前指定的Handler并调用其sendMessage()

如果您寻找该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();
}

提供的解释也很好:

从全局池中返回一个新的 Message 实例。允许我们在很多情况下避免分配新对象

obtain(Handler h):

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

    return m;
}

您可以确认obtain(Handler h)确实 obtain()添加了设置目标Handler

与 gain() 相同,但在返回的 Message 上设置目标成员的值。

还有其他几个重载,只需检查Message.java并搜索“获取”

  • obtain(Message orig)
  • obtain(Handler h, Runnable callback)
  • obtain(Handler h, int what)
  • obtain(Handler h, int what, Object obj)
  • obtain(Handler h, int what, int arg1, int arg2)
  • obtain(Handler h, int what, int arg1, int arg2, Object obj)
  • ...

希望这会有所帮助,干杯!

于 2017-02-17T19:26:09.323 回答
0

消息取自内部池,因此不会有垃圾收集开销。当你调用 Message.obtain(Hanler) 时,消息知道处理程序的接收者,当你调用 msg.sendToTarget() 时,它被传递给那个处理程序。您应该考虑使用 rxJava 库来组织并发,而不是使用 Android 的 Message 和 Handler 类 - 它更方便,您将能够用它做更复杂的事情。

于 2016-10-04T08:19:55.493 回答