观察者模式:定义了对象之间的一对多依赖,这样一来,当一个对象状态改变时,他的全部依赖者都会收到通知并自动更新。java
观察者模式涉及的角色
主题(Subject):一对多中的一,持有数据,当数据更新时,通知已注册的观察者ide
观察者(Observer):一对多中的多,接收主题数据作出响应this
一位妈妈(主题)有两个孩子,取名为小爱和小冰(观察者)。一天小爱和小冰都去找她们的朋友玩,当到了吃饭的时间,妈妈总会打电话通知她们回来吃饭(孩子默认在妈妈那注册为观察者registerObserver),但中途小冰打电话和妈妈说:“不回来吃饭了,和朋友吃”(取消观察者这角色removeObserver)。因此最后,只有小冰收到妈妈的通知,并告诉她今天买了你喜欢吃的鸡腿(notifyObserver)。spa
Person.java,Mother和Child都继承这个类[这步和讲述观察者模式没什么关系]code
public class Person { private String name; public Person(String name) { this.name = name; } public String getName() { return name; } public void setName(String name) { this.name = name; } }
Mother.javaserver
public class Mother extends Person implements Subject{ /** * 她要通知的孩子 */ private ArrayList<Observer> children = new ArrayList<>(); /** * 通知的内容 */ private String message; public Mother(String name) { super(name); } @Override public void registerObserver(Observer observer) { children.add(observer); } @Override public void removeObserver(Observer observer) { children.remove(observer); } @Override public void notifyObserver() { children.forEach(observer -> observer.message(message)); } public void sendMessage(String message) { this.message = message; // 通知她们 notifyObserver(); } }
Child.java对象
public class Child extends Person implements Observer{ public Child(String name) { super(name); } @Override public void message(String m) { System.out.println(getName() + "收到的消息:" + m); } }
Main.java继承
public class Main { public static void main(String[] args) { Mother mother = new Mother("妈妈"); Child xiaoBing = new Child("小冰"); Child xiaoAi = new Child("小爱"); // 孩子都是亲生的,吃饭时叫她们 mother.registerObserver(xiaoBing); mother.registerObserver(xiaoAi); mother.sendMessage("饭煮好了,回来吃饭,买了大家想吃的鸡腿"); System.out.println("------------------分割线-----------------------"); // 小爱说不回来吃了,取消通知她 mother.removeObserver(xiaoAi); mother.sendMessage("饭煮好了,回来吃饭,买了大家想吃的鸡腿"); } }
运行结果:接口
小冰收到的消息:饭煮好了,回来吃饭,买了大家想吃的鸡腿 小爱收到的消息:饭煮好了,回来吃饭,买了大家想吃的鸡腿 ------------------分割线----------------------- 小冰收到的消息:饭煮好了,回来吃饭,买了大家想吃的鸡腿
优势
主题与观察者之间松耦合。有新类型的观察者出现时,主题的代码不须要修改。假如咱们有一个新的具体类须要当观察者,咱们不须要为了兼容新类型而修改主题的代码,全部要作的就是在新的类里实现此观察者接口,而后注册成观察者便可。图片
就比如如上面例子,若是国家不久的未来开放三胎政策,妈妈又生了个小娜,妈妈不须要修改自身的逻辑。若是孩子要回家吃饭就实现Observer接口,妈妈那registerObserver就OK。