定义
观察者模式是一种对象行为模式,定义了对象间一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。这种模式有时又称作发布-订阅模式、模型-视图模式。
被观察者
public interface WeatherState {
//注册天气显示板块
WeatherState register(WeatherDashborad weatherState);
//移除天气显示板块
void remove(WeatherDashborad weatherState);
//通知所有的天气显示板块
void notifyAllWeatherDashborad();
}
public class Weather implements WeatherState{
private String wendu;//温度
private String shidu;//湿度
private String feng;//风
private final Set<WeatherDashborad> weatherStateSet = new HashSet<>();
public Weather register(WeatherDashborad weatherState){
weatherStateSet.add(weatherState);
return this;
}
public void remove(WeatherDashborad weatherState){
weatherStateSet.remove(weatherState);
}
public void notifyAllWeatherDashborad(){
weatherStateSet.forEach(weatherDashborad -> {
weatherDashborad.receiveResponse(wendu,shidu,feng);
});
}
public void updateWeatherDate(String wendu,String shidu,String feng){
this.wendu = wendu;
this.shidu= shidu;
this.feng = feng;
notifyAllWeatherDashborad();
}
}
观察者
public interface WeatherDashborad {
//接受天气通知
public void receiveResponse(String s1,String s2,String s3);
}
public class TV implements WeatherDashborad{
@Override
public void receiveResponse(String s1, String s2, String s3) {
System.out.println("=======电视显示====");
System.out.println("温度:"+s1);
System.out.println("湿度:"+s2);
System.out.println("风:"+s3);
}
}
public class Phone implements WeatherDashborad{
@Override
public void receiveResponse(String s1, String s2, String s3) {
System.out.println("=======手机显示====");
System.out.println("温度:"+s1);
System.out.println("湿度:"+s2);
System.out.println("风:"+s3);
}
}
测试
public class Client {
public static void main(String[] args) {
Weather weather = new Weather();
Phone phone = new Phone();
TV tv = new TV();
weather.register(phone).register(tv);
weather.updateWeatherDate("36","11","cold");
weather.remove(phone);
weather.updateWeatherDate("35","15","cold");
}
}
=======手机显示====
温度:36
湿度:11
风:cold
=======电视显示====
温度:36
湿度:11
风:cold
=======电视显示====
温度:35
湿度:15
风:cold
Process finished with exit code 0
jdk内置观察者
Observable(被观察者)
Observer(观察者)
实现的方式也和上面类似,有兴趣的可以看下
public class QQ extends Observable {
private String msg;
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
setChanged();
notifyObservers("from QQ message....");
}
}
public class UserOne implements Observer {
@Override
public void update(Observable o, Object arg) {
QQ qq= (QQ)o;
String msg = qq.getMsg();
System.out.println(arg);
System.out.println("会员收到:"+msg);
}
}
public class UserTwo implements Observer {
@Override
public void update(Observable o, Object arg) {
QQ qq= (QQ)o;
String msg = qq.getMsg();
System.out.println(arg);
System.out.println("用户收到:"+msg);
}
}
public class Client {
public static void main(String[] args) {
QQ qq = new QQ();
qq.addObserver(new UserOne());
qq.addObserver(new UserTwo());
qq.setMsg("123");
}
}
from QQ message....
用户收到:123
from QQ message....
会员收到:123
Process finished with exit code 0
优缺点
优点
耦合度较低,两者之间的关联仅仅在于消息的通知
缺点
观察者同时也可能是被观察者,消息传递的链路可能会过长,完成所有通知花费时间较多
观察者和被观察者之间产生循环依赖,或者消息传递链路形成闭环,会导致无限循环