当对象存在一对多关系时,则使用观察者模式(observer pattern)。比如一个对象修改了,则会通知其所有依赖对象,此模式属于行为模式。
定义对象见一对多的关系,当一个对象的状态发生改变时,所有依赖它的对象都得到通知并自动更新。
一个对象改变给其他对象通知的问题,而且要考虑到易用和低耦合,保证高度协作。
一个对象(目标对象)的状态发生改变,所有的依赖对象都得到通知,进行广播通知。
使用面向对象技术,可以将这种依赖关系弱化。
在抽象类有一个ArrayList存放观察者们。
1.拍卖的时候,拍卖师观察到最高价,通知给竞价者。
观察者和被观察者是抽象耦合的,2.建立一套出发机制。
1.如果一个被观察者对象有很多的直接和间接的观察者的话,将所有的观察者通知会话很长时间。2.如果在观察者和观察目标之间有循环依赖的话,观察目标会触发他们的循环调用,可能导致系统崩溃。3.观察者模式没有响应的机制让观察者知道所观察的目标是怎样发生变化的而仅仅知道观察目标发生了变化。
一个抽象模型有两个方面,其中一个方面依赖于另外一个方面,将这些方面封装在独立的对象中使它们独自改变和使用;
一个对象的改变将导致其他一个或多个对象也发生改变,而不知道具体有多少对象将发生改变,可以降低对象的耦合度;
一个对象必须通知其他对象,而并不知道这些对象时谁;
需要在系统中创建一个触发链,A对象的行为将影响b,b->c,…可以使用观察者模式创建一种链式触发机制;
1.JAVA 中已经有了对观察者模式的支持类;2.避免循环使用;3.如果顺序执行,某一观察者错误会导致阻塞,所以一般采用异步。
代码:
被观察者:其中通知的代码写在要更新的方法里
package com.observer.beObservered;
import java.util.ArrayList;
import java.util.List;
public class Subject {
private List observers = new ArrayList<>();
private int state;
public List getObservers() {
return observers;
}
public void setObservers(List observers) {
this.observers = observers;
}
public int getState() {
return state;
}
public void setState(int state) {
this.state = state;
notifyAllObservers();//通知方法
}
public void attach(Observer observer){
observers.add(observer);
}
public void notifyAllObservers(){
for(Observer o : observers){
o.update();
}
}
}
观察者
抽象类
package com.observer.beObservered;
public abstract class Observer {
protected Subject subject;
public abstract void update();
}
实现类
package com.obverser.obversers;
import com.observer.beObservered.Observer;
import com.observer.beObservered.Subject;
public class HexaObserver extends Observer{
public HexaObserver(Subject subject){
this.subject = subject;
this.subject.attach(this);
}
@Override
public void update() {
System.out.println("haxa:"+Integer.toHexString(this.subject.getState()));
}
}
package com.obverser.obversers;
import com.observer.beObservered.Observer;
import com.observer.beObservered.Subject;
public class OctalObserver extends Observer{
public OctalObserver(Subject subject){
this.subject = subject;
this.subject.attach(this);
}
@Override
public void update() {
System.out.println("octal:"+Integer.toOctalString(subject.getState()));
}
}
package com.obverser.obversers;
import com.observer.beObservered.Observer;
import com.observer.beObservered.Subject;
public class BinaryObserver extends Observer{
public BinaryObserver(Subject subject){
this.subject = subject;
this.subject.attach(this);
}
@Override
public void update() {
System.out.println("binary:"+Integer.toBinaryString(subject.getState()));
}
}
测试类
package com.observer.test;
import org.junit.Test;
import com.observer.beObservered.Subject;
import com.obverser.obversers.BinaryObserver;
import com.obverser.obversers.HexaObserver;
import com.obverser.obversers.OctalObserver;
public class TestDemo {
@Test
public void test(){
Subject subject = new Subject();
subject.setState(96);
new BinaryObserver(subject);
new HexaObserver(subject);
new OctalObserver(subject);
subject.setState(100);
}
}
控制台打印
binary:1100000
haxa:60
octal:140
binary:1100100
haxa:64
octal:144