面临问题:
对象之间经常存在这样一种关系:某个对象状态的改变将导致另外一些对象状态变化(比如“文档存储-文档展示”关系)。
也就是说,交通灯和汽车,汽车依赖于交通灯,交通灯要通知汽车,但不知道要通知多少汽车。通知这是一种行为,但是通知的话,必须要有对象,但是一个交通灯对每一辆汽车都发一个通知,这样产生了紧密的耦合。怎样才能解耦呢?
解决方案:
当一个抽象模型有两个方面, 其中一个方面依赖于另一方面。可以将这二者封装在独立的对象中以使它们可以各自独立地改变和复用。
将对象分为两类——主体(subject,被观测的目标)和观测者(observer),他们之间是一对多的关系;二者之间的关系在运行时动态建立——observer向subject注册,然后当subject的某个事件发生时,通知observer行动。
观察者模式中的关键对象是目标(subject)和观察者(observer)。一个目标可以有任意数目的依赖它的观察者。一旦目标的状态发生改变, 所有的观察者都得到通知。作为对这个通知的响应,每个观察者都将查询目标以使其状态与目标的状态同步。
我的个人见解:既然是行为型模式,那就是封装变化的行为,但是观察者模式的行为是通知观察者,由于观察者是变化的,就会导致行为的变化。即观察者数目变化,会导致行为变化。那就要将观察者封装起来。而主体也可能变化。所以有了具体的主体。来通知观察者的变化。感觉很类似桥接模式,两个维度都会发生变化。这个观察者模式,是对行为来说的。而桥接是对对象来说的。所有一个是关于行为的,一个是关于对象的。(有错误请指正)
有的东西变化或者发生某件事情的时候,可能引发其他一些对象的行为。 或者说,有些对象作为观察者在始终盯着某个对象,一旦有事发生就需要立即行动
生活中的例子:
交通灯和汽车:汽车是观察者,红绿灯是汽车观察的目标。
绿灯变红,则汽车停止; 变绿则汽车启动。
Subject(目标)
目标知道它的观察者。可以有任意多个观察者观察同一个目标。提供注册和删除观察者对象的接口。
Observer(观察者)
为那些在目标发生改变时需获得通知的对象定义一个更新接口。
ConcreteSubject(具体目标)
将有关状态存入各ConcreteObserver对象。当它的状态发生改变时, 向它的各个观察者发出通知。
ConcreteObserver(具体观察者)
维护一个指向ConcreteSubject对象的引用。存储有关状态,这些状态应与目标的状态保持一致。实现Observer的更新接口以使自身状态与目标的状态保持
一致。
具体主体代码:
public class ConcreteSubject extends Subject
{
public void attach(Observer observer)
{
observers.add(observer);
}
public void detach(Observer observer)
{
observers.remove(observer);
}
public void notify()
{
for(Object obs:observers)
{
((Observer)obs).update();
}
}
}
具体主体,可以对update传入一定的参数,是具体观察者得到参数之后,调用自己的方法,实时更新数据等等。