设计模式之观察者模式

观察者模式(Observer):定义对象间的一种一对多依赖关系,当一个对象的状态发生改变时,所有依赖于他的对象都得到通知并被自动更新。

场景问题
订阅报纸的问题:
    订阅者类向出版者类订阅报纸,很明显不会只有一个订阅者订阅报纸,订阅者类可以有很多;当出版者类出版新报纸的时候,多个订阅者类如何知道呢?还有订阅者类如何得到新报纸的内容呢?
具体描述
当报社有新报纸出版的时候
多个订阅报纸的人员
如何知道?
订阅报纸的人员需要得到新报纸的内容,要看这些新内容
对应的对象描述
当出版者类状态发生改变的时候
多个订阅者类
如何能得到通知?
订阅者类会相应的进行什么样的处理或改变

解决方案:
    使用观察者模式来处理这种问题。观察者模式把这多个订阅者称为观察者:Observer,多个观察者观察的对象被称为目标:Subject
    一个目标可以有任意多个观察者对象,一旦目标的状态发生了改变,所有注册的观察者都会得到通知,然后多个观察者会对通知作出相应的响应,执行相应的业务功能处理,并使自己的状态和目标对象的状态保持一致。

观察者模式的结构和说明

  • Subject:目标对象,通常具有如下功能。
    • 一个目标可以被多个观察者观察
    • 目标提供对观察者注册和退订的维护
    • 当目标的状态发生变化时,目标负责通知所有注册的、有效的观察者
  •   Observer:定义观察者的接口,提供目标通知时对应的更新方法,这个更新方法进行相应的业务处理,可以在这个方法里面回调目标对象,以获取目标对象的数据。
  • Concrete Subject:具体的目标实现对象,用来维护目标状态,当目标对象的状态发生改变时,通知所有注册的有、有效的观察者,让观察者执行相应的处理
  • Concrete Observer:观察者的具体实现对象,用来接收目标的通知,并进行相应的后续处理,比如更新自身的状态以保持和目标的相应装填一致
认识观察者模式
  • 目标和观察者之间的关系:目标和观察者之间是典型的一对多的关系
  • 单向依赖:在观察者模式中,观察者和目标都是单向依赖的,只有观察者依赖于目标,而目标是不会依赖于观察者的。主动权掌握在目标手中,只有目标知道什么时候需要通知观察者
  • 基本的实现说明
  • 命名建议
    • 观察者模式又被称为发布-------订阅模式
    • 目标接口的定义,建议在名称后面跟Subject
    • 观察者接口的定义,建议在名称后面跟Observer
    • 观察者接口的更新方法,建议名称为Update,当然方法的参数可以根据的需要定义,参数个数不限、参数类型不限
  • 触发通知的时机
  • 相互观察
  • 观察者模式的调用顺序示意图
  • 通知的顺序
观察者模式的优缺点
观察者模式具有以下优点:
  • 观察者模式实现了观察者和目标之间的抽象耦合
    • 原本目标对象在状态发生改变的时候,需要直接调用所有的观察者对象,但是抽象出观察者接口以后,目标和观察者就只是在抽象层面上耦合了,也就是说目标只是知道观察者接口,并不知道具体的观察者的类,从而实现目标类和具体的观察者之间的解耦。
  • 观察者模式实现了动态联动
    • 所谓联动,就是做一个操作会引起其他相关的操作。由于观察者模式对观察者注册实行管理,那就可以在运行期间,通过动态地控制注册的观察者,来控制某个动作的联动范围,从而实现动态联动。
  • 观察者模式支持广播通信
    • 由于目标发送通知给观察者是面向所有注册的观察者,所以每次目标通知的信息就要对所有注册的观察者进行广播。当然,也可以通过在目标上添加新的功能来限制广播的范围。
观察者模式的缺点是:
  • 可能会引起无谓的操作
思考观察者模式
  • 观察者模式的本质:当修改目标对象的状态的时候,就会触发相应的通知,然后会循环调用所有注册的观察者对象的相应方法,其实就相当于联动调用这些观察者的方法。这个联动还是动态的,可以通过这车和取消注册来控制观察者,因而可以在程序运行期间,通过动态地控制观察者,来变相地实现添加和删除某些功能处理,这些功能就是观察者在update的时候执行的功能。同时目标对象和观察者对象的解耦,又保证了无论观察者发生怎样的变化,目标对象总是能够正确地联动过来。
  • 何时选用观察者模式
    • 当一个抽象模型有两个方面,其中一个方面的操作依赖于另外一个方面的状态变化,那么就可以选用观察者模式,将这两者封装成观察者和目标对象,当目标对象变化的时候,依赖于它的观察着对象也会发生相应的变化。
    • 如果在更改一个对象的时候,需要同时连带改变其他的对象,而且不知道究竟有多少对象需要被连带改变,这种情况下可以选用观察者模式,被更改的那一个对象很明显就相当于是目标对象,而需要连带修改的多个其他对象,就作为多个观察者对象了。
    • 当一个对象必须通知其他的对象,但是你又希望这个对象和其他被它通知的对象是松散耦合的。
  • 观察者模式和状态模式
            观察者模式和状态模式是有相似之处的。
            观察者模式是当目标状态发生改变时,触发并通知观察者,让观察者去执行相应的操作。而状态模式是根据不同的状态,选择不同的实现,这个实现类的主要功能就是针对状态相应地操作,它不像观察者,观察者本身还有很多其他的功能,接收通知并执行相应处理只是观察者的部分功能。
            当然观察者模式和状态模式是可以结合使用的。观察者模式的重心在触发联动,但是到底决定哪些观察者会被联动,这时就可以采用状态模式来实现了,也可以采用策略模式来进行选择需要联动的观察者。
  • 观察者模式和中介者模式
            观察者模式和中介者模式是可以结合使用的。
            如果观察者和被观察的目标之间的交互关系很复杂,比如,有一个界面,里面有三个下拉列表组件,分别选择国家、省份/州、具体的城市,很明显这是一个三级联动,当你选择一个国家的时候,省份/州应该相应改变数据,省份/州一改变,具体的城市也需要相应改变。

concrete
['kɒŋkriːt] ['kɑŋkrit]

  • adj. 混凝土的;实在的,具体的;有形的
  • vi. 凝结
  • vt. 使凝固;用混凝土修筑
  • n. 具体物;凝结物
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值