是否有理由在广播接收器上使用观察者模式?

时间:2014-04-17 21:39:46

标签: java android

最近,我开始研究停止使用广播接收器的Android项目,以支持"听众"。实际上,这个实现正在使用类似于this article的观察者模式(在我的例子中,甚至涉及.aidl)。

我无法理解的是为什么。我被教导说,作文比继承更好。对我来说,广播接收器就是一个组合。这是一个原生的Android功能,每个Android开发人员都应该熟悉它。那么,为什么我有理由放弃我的广播接收器以支持观察者模式?这只是我团队中糟糕设计的产物吗?

更新

我确实找到了一条评论,声明这是遵循Single Responsiblity,但是我不确定我是否遵循,因为任何实现侦听器的类都必然会有其他任务(例如,活动,管理UI的人)生命周期)。

2 个答案:

答案 0 :(得分:10)

使用BroadcastReceiver s可以将一个组件与另一个组件分离。发件人对其消息的接收者一无所知。它只是发送广播,并不关心它是否被接收和处理。相同的概念有一个事件总线(例如Otto)。但是全局BroadcastReceiver的开销很小,因为它们本质上是一个跨应用程序。因此,如果您只需要在一个应用程序内发送事件,我将使用LocalBroadcastManager或我之前指出的事件总线。

在使用监听器(观察者)的情况下,组件变得紧密耦合,因为发送者具有对接收者的引用并且知道它的性质(监听器实现什么接口)并且必须检查监听器是否不为空。 / p>

答案 1 :(得分:0)

是的,我已经看过100次BroadcastReceiver使用Observer设计模式,但仍然非常不同意这一点。  首先,Observer设计模式的定义是:“观察者模式是一种软件设计模式,其中一个称为主体的对象维护其依赖者列表,称为观察者,并自动通知他们任何状态变化,通常通过调用他们的方法之一“。在BroadcastReceiver中观察到什么对象?  ctx.registerReceiver(接收器,过滤器)不提供有关任何对象的信息。广播接收机的想法不是专门用于通知类的数量有关任何对象的变化 - 它只是广播机制的监听器,而不仅仅是。要获得有关更改的通知,您必须使用过滤器注册接收器对象。一旦未设置带接收器的过滤器,您将收到NO NOTIFICATION。因此,应根据意图的动作选择接收器,以便触发onReceive(Intent,...)。至少我在这里看到选择器模式。但不仅如此。真正播出的是什么?它传播的意图已经像集线器一样发送,并通过操作过滤器选择已注册的接收器。现在看看中介模式的定义(https://sourcemaking.com/design_patterns/mediator)。不是这样吗?广播机制实现了启用对象交互的技能,其中发送者对侦听器一无所知,并且监听器说出无论谁发送了什么都要听。是不是调解器 基本上,BroadcastReceiver是Android广播机制不可分割的一部分。从整个机制中分离BroadcastReceiver根本就不正确。从而像JMS消息消费者是JMS不可分割的一部分。 在广播接收器中使用的Intent专用于传输动作和参数包(参数,还有其他)。它通常用于传输动作(!)和数据。真的,它是命令的数据对象。 为了进行比较,让我们考虑Android中Observer模式的一个众所周知的案例是ContentObserver。这个怎么运作:  getContentResolver()。 registerContentObserver(SOME_URI,true,yourObserver);请注意,侦听器附加到专用资源,而不是用于通用侦听。一旦内容发生变化就触发它(你发送了关于任何事情的通知吗?)并通知了什么是改变的(Uri)。是的,这真的是观察者。它通知关于对象的变化,并且监听者 - 观察者看到观察对象中发生了什么变化。它是广播的工作模式吗? 在广播中,我看到元素至少是中介,选择器和DTO。