观察者模式也是我们非常常用的设计模式之一
我们先举个例子来初步认识一下观察者模式
当我们在打团队游戏时,当你受到攻击需要队友帮忙时该怎么办?
这时候就需要给你所有的队友发送一条你正在被攻击的消息。所有的队友会根据你发送的消息作出相应的动作。比如有团队意识来帮你,或者不帮你继续玩自己的。
这里面的队员就是该设计模式名字中的观察者。那么受到攻击的自己的是什么呢。被观察者?不,准确的我们称之为目标或者主题。
所以整个流程大概就是:当目标(主题)的状态发送改变时就会通知观察者,观察者根据自己的情况做出相应的动作。
看过了上面的例子,我们再来看一下观察者模式的正经定义:定义对象之间的一对多依赖关系,使得每当一个对象状态发生改变时,其相关依赖对象皆得到通知并被自动更新。
这里我们看到这个一对多的关系,目标(主题)就是那个一,它对应的多个观察者就是多,他们之间存在着依赖的关系。
我们再来看一下它的结构图:
然后我们来根据这个结构图用java代码实例帮助我们更近一步的理解
这里我们把所有的Observe都存入ArrayList中来完成我们一对多的依赖
//目标抽象类
abstract class Subject {
//定义一个观察者集合
ArrayList<Observe> observes = new ArrayList();
//把观察者对象添加到观察者集合中
public void attach(Observe observe) {
observes.add(observe);
}
//把观察者对象从观察者集合中删除
public void detach(Observe observe) {
observes.remove(observe);
}
//声明通知观察者的抽象方法
public abstract void notifyObserve();
}
目标的具体实现类中实现了notifyObserve()方法
这里用到了增强for循环的方法,不会的可以去百度看一看,这样就给每一个观察者都通知了
//目标具体实现类继承抽象类
class ConcreteSubject extends Subject {
@Override
public void notifyObserve() {
System.out.println("目标状态已更新... 发送通知给观察者中...");
//发送通知给观察者
for (Observe observe : observes) {
observe.update();
}
}
}
然后是观察者的接口,里面有一个更新的方法。
//观察者接口
interface Observe {
void update();
}
我们再实现具体的观察者,实现具体的updata()方法之中的内容
//具体的观察者
class ConcreteObserver implements Observe {
private String name;
public ConcreteObserver(String name) {
this.name = name;
}
@Override
public void update() {
System.out.println(name + "更新一下我的状态...");
}
}
然后再写一个测试方法
public class ObservePattern {
public static void main(String[] args) {
Subject subject = new ConcreteSubject();
Observe observe1 = new ConcreteObserver("玩家1");
Observe observe2 = new ConcreteObserver("玩家2");
subject.attach(observe1);
subject.attach(observe2);
subject.notifyObserve();
}
}
得到结果:
这样我们就实现了我们的观察者模式,实现了目标对观察者的通信
我们还可以实现很多的观察者完成不同的操作,例如有的观察者收到消息之后选择更新自己的状态,当然也可以有的观察者选择不更新自己的状态。
我们继续实现一个不同的观察者
class ConcreteObserveOther implements Observe{
private String name;
public ConcreteObserveOther(String name) {
this.name = name;
}
//在更新方法中与上一个观察者的做法不同
@Override
public void update() {
System.out.println(name + "收到了消息但是选择不更新...");
}
}
这就实现了每个人有不同的回应…
通过上文相信大家都对观察者设计模式有了一定的认识,显然它是满足开闭原则的增加新的具体观察者无须修改原有的系统代码。还降低了一对多系统的设计难度。
但是同时如果一个目标有大量的观察者,这也是很耗时间的。并且如果观察者之间如果存在循环依赖的话就可能会死循环。
最后祝大家期末顺利!!
参考链接:https://www.jianshu.com/p/186a0041ac5b