4

问题:

与在 Android中使用Messenger到 Messenger 通信相比,使用Handler到 Handler 通信是否“更好”(= 更快且开销更少) ?

情况:

具有一堆活动和一个正在运行的服务(已启动服务)的 Android 应用程序。在服务中,有几个线程在服务的主线程旁边运行。应用程序启动,第一个活动启动服务,服务启动,第一个活动转发到第二个活动,第二个活动绑定到服务,...

处理程序到处理程序:

...服务分发对服务处理程序的引用,第二个活动定义了自己的处理程序,第二个活动现在可以使用服务处理程序直接与服务通信。为了让服务处理程序知道它必须回复活动处理程序,可以使用Message对象中的msg.obj字段来设置“回复”处理程序(= 活动中的处理程序)。现在,活动和服务之间的双向通信已成功建立。

信使到信使:

...服务分发对服务信使的引用,第二个活动定义了自己的信使,第二个活动现在可以使用服务信使间接与服务通信,服务信使将消息(消息对象)转换为 Parcelable 对象,然后重新转换 Parcelable对象返回到一个新的(但相等的)消息对象,该对象被移交给服务的处理程序。为了让服务信使知道它必须回复活动信使,可以使用活动中的信使设置msg.replyTo字段。双向通信成功建立。

问题”:

当我只需要在我的应用程序中仅在一个进程的边界内进行直接通信时,为什么我需要 Messenger 到 Messenger 设置?一个进程中的所有线程都可以通过使用它们的处理程序轻松进行通信(假设这些线程都正确设置了自己的处理程序)。我不希望信使首先将在两个处理程序之间共享的消息对象展平,这只是增加了开销,除了“盲目地遵循 Android 服务教程”之外没有任何目的。

可能的解决方案:

启动服务,绑定一次,让服务分发一个本地绑定器对象,在 onServiceConnected() 的 ServiceConnection 实现中设置 Activity 中的服务处理程序,让 Activity 将其存储在全局内存空间中的某个位置,切换到第三,第四,第五个活动,您不必在所有其他活动中再次绑定,因为所有活动都知道自己的处理程序(在每个活动中单独设置)并且可以从全局内存空间中获取服务处理程序。如果服务需要响应第四个活动的处理程序,第四个活动只需将自己的处理程序(fourthHanlder)添加到 msg.obj 字段,服务就知道必须将回复消息发送到哪里。就是这样。

除此之外:活动在 ui-thread/main-thread 上运行,服务也在 ui-thread/main-thread 上运行,所以实际上它们是同一个线程的一部分,只是不同的处理程序。或者这是我的错误想法?

这意味着整个 Messenger 只是同一进程中线程之间的本地(内部)通信的额外开销!不需要,除非 Android 系统在内部确定 Messenger 是否在同一进程内相互通信并绕过消息的扁平化并跳过转换为 Parcelable 对象,以便 Messenger 实际上在处理程序本身之间直接通信(无需用户/程序员实际上意识到了这一点。如果这是我现在所想的,那么至少我不知道这一点)。

我看到只有三种方法可以通过以下方式在活动和服务之间创建异步通信:

  • 意图(不能发送带有意图的对象!)
  • 信使(与直接使用处理程序相比,可能性有限,例如:您不能将消息排队到队列的前面)
  • 处理程序(仅当处理程序所属的线程在同一进程中时才有可能,否则您确实需要信使)

我相信处理程序是线程之间通信的最快方式,其次是信使,最后是意图。这是真的???

请分享您对此事的见解和经验,即使我看错了:) 谢谢。

4

1 回答 1

9

我看到只有三种方法可以在活动和服务之间创建异步通信

废话。

现在,我会使用事件总线进行服务->活动通信(LocalBroadcastManagerSquare 的Otto,greenrobot 的EventBus)。无需绑定,无需自己绑定,无需自己绑定,Handler灵活性Messenger更大。

除此之外,如果您使用绑定,只需创建自己的侦听器接口,与使用 anOnClickListener侦听按钮单击的方式没有什么不同。唯一的变化是除了接收事件之外,您还将引发事件(调用侦听器上的方法)。

而且,还有ResultReceiver,虽然我没有看到它使用得这么多。

于 2013-10-26T22:54:43.587 回答