描述

观察者模式定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新,也称发布-订阅(Publish/Subscribe)模式,这是一种行为型模式(Behavioral),主要用于描述类或对象怎样交互以及怎样分配职责。观察者模式中通常包括观察目标和观察者两个继承层次结构,可实现观察者和目标之间的抽象耦合,同时实现了对象之间的动态联动。

文字太抽象?可以先不管,直接往下看案例,回过头来再看定义,就很简单了:

场景举例

通过学校放学打铃,所有在校人员听到后,做出反应,可以比较形象的理解观察者模式,如下图:

观察者模式在类设计的时候会用到四个内容:

代码案例

案例源码

https://gitee.com/sujianfeng/design-pattern

被观察者抽象类:学校铃声

public abstract class AbstractSchoolBell {/*** 增加观察者* @param schoolPerson 入校人员*/abstract void attach(AbstractSchoolPerson schoolPerson);/*** 剔除观察者* @param schoolPerson 离校人员*/abstract void detach(AbstractSchoolPerson schoolPerson);/*** 广播通知(铃声)*/abstract void notifyBell();}

被观察者:放学铃声

public class LeveSchoolBell extends AbstractSchoolBell {private List<AbstractSchoolPerson> schoolPersonList = new ArrayList<>();@Overridepublic void attach(AbstractSchoolPerson schoolPerson) {schoolPersonList.add(schoolPerson);}@Overridepublic void detach(AbstractSchoolPerson schoolPerson) {schoolPersonList.remove(schoolPerson);}@Overridepublic void notifyBell() {//广播通知所有在校人员for (AbstractSchoolPerson schoolPerson : schoolPersonList){schoolPerson.listenBell(this);}}
}

观察者抽象类:在校人员

public abstract class AbstractSchoolPerson {/*** 监听铃声*/abstract void listenBell(AbstractSchoolBell abstractSchoolBell);
}

观察者:学生

public class Student extends AbstractSchoolPerson {@Overridepublic void listenBell(AbstractSchoolBell schoolBell) {System.out.println("收拾书包!");}
}

观察者:老师

public class Teacher extends AbstractSchoolPerson {@Overridepublic void listenBell(AbstractSchoolBell schoolBell) {System.out.println("收拾教案!");}
}

观察者:门卫

public class Guard extends AbstractSchoolPerson {@Overridepublic void listenBell(AbstractSchoolBell schoolBell) {System.out.println("打开学校大门!");}
}

单元测试

public class ObserverTest {@Testpublic void test(){//放学铃声LeveSchoolBell leveSchoolBell = new LeveSchoolBell();//学生Student student = new Student();//老师Teacher teacher = new Teacher();//门卫Guard guard = new Guard();//学校人员leveSchoolBell.attach(student);leveSchoolBell.attach(teacher);leveSchoolBell.attach(guard);//下课铃声响了leveSchoolBell.notifyBell();}
}

Java自带的观察者模式

在java.util包中包含有基本的Observer接口和Observable抽象类.功能上和SchoolBell 接口和SchoolPerson 接口类似.不过在使用上,就方便多了,因为许多功能比如说注册,删除,通知观察者的那些功能已经内置好了。使用javaAPI的观察者模式需要明白这么几件事情:

如何使对象变为观察者?

实现观察者接口(java.util.Observer),然后调用Observable对象的addObserver()方法.不想再当观察者时,调用deleteObserver()就可以了.

被观察者(主题)如何发出通知?

第一步:先调用setChanged()方法,标识状态已经改变的事实.

第二步:调用notifyObservers()方法或者notifyObservers(Object arg),这就牵扯到推(push)和拉(pull)的方式传送数据.如果想用push的方式"推"数据给观察者,可以把数据当做数据对象传送给notifyObservers(Object arg)方法,其中的arg可以为任意对象,意思是你可以将任意对象传送给每一个观察者.如果调用不带参数的notifyObserver()方法,则意味着你要使用pull的方式去主题对象中"拉"来所需要的数据.

观察者如何接收通知?

观察者只需要实现一个update(Observable o,Object arg)方法,第一个参数o,是指定通知是由哪个主题下达的,第二个参数arg就是上面notifyObserver(Object arg)里传入的数据,如果不传该值,arg为null.

思考

观察者模式的意义是什么?观察者模式比较简单,大家理解后,就可以很轻松的回答这个问题,这里就不写了,留给大家自己总结。

学校放学铃声响了...3分钟理解【观察者模式】相关推荐

  1. 基于FPGA的学校打铃器(VHDL)

    基于FPGA的学校打铃器(VHDL) (20年齐工大某汪老师课设)具体资源后续发 此试验箱数码管自带译码器,显示BCD码 一.具体功能 1.打铃器具备电子钟的24小时.60分和60秒计时功能,可对时间 ...

  2. java弱引用怎么手动释放,十分钟理解Java中的弱引用,十分钟java引用

    十分钟理解Java中的弱引用,十分钟java引用 本篇文章尝试从What.Why.How这三个角度来探索Java中的弱引用,帮助大家理解Java中弱引用的定义.基本使用场景和使用方法.由于个人水平有限 ...

  3. 一分钟理解Java包装类型

    转载自  一分钟理解Java包装类型 Java 一直标榜自己是一个纯粹的面向对象语言,自作聪明的为所有的值类型都提供相应的引用类型(不明白这两个概念,看之前的<一分钟理解传值和传引用>)比 ...

  4. 一分钟理解Java公平锁与非公平锁

    转载自  一分钟理解Java公平锁与非公平锁 和朋友聊天他提到:ReentrantLock 的构造函数可以传递一个 bool 数据,true 时构造的是"公平锁".false 时构 ...

  5. 五分钟理解什么是面向对象

    昨天讲了MVC,有同学表示还想了解一些软件开发架构方面的姿势.我琢磨了半天,列了不少技术名词,本来想挑一个出来讲一讲,写了一半发现有很多前置知识之前没涉及,于是决定把坑填一填,先从基础的「面向对象」讲 ...

  6. 5分钟理解边缘概率,联合概率,条件概率,随机事件独立,随机事件依赖

    在隐马尔可夫(HMM)和条件随机场(CRF)中有很多概率计算问题,要想理解他们,必须先把概率的一些概念及计算公式搞清楚.本文旨在用形象的图形和具体事例来讲解这些概念和公式,以帮助理解.这里讲的部分内容 ...

  7. 5分钟理解Iass Pass SasS三种云服务区别

    5分钟理解Iass Pass SasS三种云服务区别 其实搞懂这个问题也不难,我们可以把云计算理解成一栋大楼,而这栋楼又可以分为顶楼.中间.低层三大块. 那么我们就可以把Iass(基础设施).Pass ...

  8. 五分钟理解什么是接口

    五分钟理解什么是接口   在IT和互联网领域里面,这个词在不同场景下都会出现,比如"USB接口","让后台给我提供一个接口,我直接调用这个接口","这 ...

  9. unity 3分钟理解 批处理和drawcall有什么区别

    3分钟理解 批处理和drawcall有什么区别? 本人技术有限,如有错误,请道友们留言讨论,切勿口吐芬芳. 正文-------------------------------------------- ...

最新文章

  1. linux-多任务同步和互斥
  2. 052_Function对象
  3. 如何设置listview每个item高度
  4. SQL99标准中的查询(MySQL)
  5. 从实例入手学习Shiro自定义Realm实现查询数据进行验证
  6. 激发新型城市创新动能 第四范式分享智慧城市探索之路
  7. Nvidia: Mx150 CUDA10安装驱动
  8. 深度学习(1)深度学习初见
  9. 优秀的开源项目C_适合提高C/C++、网络编程能力的开源项目!不要错过,赶紧收藏...
  10. python3 实现对比conf 文件差异
  11. 卷片机行业调研报告 - 市场现状分析与发展前景预测
  12. NGUI中的Table自定义排序
  13. java实现打印菱形(任意输入数字打印任意阶菱形)
  14. mysql基本语法 外键_MySQL语法创建外键?
  15. 变频器维修技术之OC故障解决方案
  16. live555源码分析(七)播放过程
  17. 【Midjourney教程】设计麻瓜也能10分钟上架一套表情包
  18. mysql 批量查找 in_在数据库查询时解决大量in 关键字的方法
  19. 芯旺微车规级功夫KF32A150,SPI调试经验
  20. 一个大专生从8K到13K的挫折经历

热门文章

  1. 求购 pcqq 安卓 协议 云控
  2. PoS即股权证明(Proof of Stake)
  3. linux终端下修改文件夹名称显示颜色
  4. python爬取客流数据_【python爬取雅虎财经数据】“五一”和广交会客流叠加 广州出入境客流呈“双高峰”...
  5. OLE对象是什么?为什么要在CAD图形中插入OLE对象?
  6. python3.7.1 内置函数
  7. 消费者组 Consumer Group 和 重平衡 Rebalance
  8. idea中git账号输错后如何删除缓存账户信息重新输入正确信息
  9. 【毕业设计】基于微信小程序的超市购物系统
  10. 易格售后服务管理系统 v2.0 单机版 绿色