- 观察者模式
定义了对象之间的一对多依赖,这样一来,当一个对象改变状态时,它的所有依赖者都会收到通知并自动更新。
- 应用分析——一对多对应关系实现
当多个观察者对象需要依赖一个主题对象的状态而动态变化时,使用观察者模式,当主题状态改变时,会通知观察者,观察者收到通知产生相应的状态更新。
- 实例介绍——气象监测装置,有一个气象对象(主题对象),动态改变,多个显示装置(观察者对象),如:目前状况、气象统计和天气预报,实现当气象改变时,三个显示布告板同步变化。
- 代码分析
//Observer.h
//观察者
#ifndef OBSERVER_H
#define OBSERVER_H
#include <iostream>
class Observer//观察者接口
{
protected:
float temperature;
float humidity;
float pressure;
public:
void update(float t,float h,float p)
{
temperature=t;
humidity=h;
pressure=p;
display();
}
virtual void display()=0;
virtual ~Observer(){}
};
class CurrentBroad:public Observer//当前状态观察者
{
public:
void display()
{
std::cout<<"Current conditions: "<<temperature<<"F "<<humidity<<"% humidity"<<std::endl;
}
};
class ForecastBroad:public Observer//预告状态观察者
{
public:
void display()
{
std::cout<<"Forecast conditions: "<<pressure<<" pressure"<<std::endl;
}
};
#endif
//WeatherData.h
//主题
#ifndef WEATHERDATA_H
#define WEATHERDATA_H
#include <list>
#include "Observer.h"
class Observer;
class Subject//主题接口
{
protected:
std::list<Observer*> observerList;//用链表方便删除
public:
void registerObserver(Observer *O)
{
observerList.push_back(O);
}
void removeObserver(Observer *O)
{
observerList.remove(O);
}
virtual void notifyObserver()=0;
virtual ~Subject(){}
};
class WeatherData:public Subject//具体主题类
{
private:
float temperature;
float humidity;
float pressure;
public:
void setcondition(float t,float h,float p)
{
temperature=t;
humidity=h;
pressure=p;
notifyObserver();
}
void notifyObserver()
{
std::list<Observer*>::iterator iterator_tem=observerList.begin();
for(;iterator_tem!=observerList.end();++iterator_tem)
(*iterator_tem)->update(temperature,humidity,pressure);
}
};
#endif
//main.cpp
//测试程序
#include <iostream>
#include "WeatherData.h"
int main()
{
WeatherData *w=new WeatherData();//主题对象
Observer *O1=new CurrentBroad();//观察者对象
Observer *O2=new ForecastBroad();
w->registerObserver(O1);//注册观察者
w->registerObserver(O2);
w->setcondition(10,20,30);
w->removeObserver(O1);//移除观察者
w->setcondition(100,100,100);
delete w;
delete O1;
delete O2;
return 0;
}