c++ 中的观察者模式
2015-12-04 19:04
627 查看
观察者模式:
是讲有一个目标,众多个观察者去“观察”目标。目标是目标抽象类的一个派生类,观察者是观察者抽象类的一个派生类。当目标类的数据改变,所有对应的观察者对应去更新自己的状态。注意观察者处于被动地位,被观察者处理主动地位。
应用场景
比如有一个世界时钟程序,有多个图形时钟去显示比如北京时区,巴黎时区,等等。如果设置一个北京时间,那么其他时钟图形都需要更新(加上或者减去时差值)。典型的图形界面设计随处可见,一个温度程序,在温度湿度等条件改变时,要更新多种显示图形来呈现。
UML图示
原本是子类间进行耦合,把子类间的耦合提升到父类中去,这样父类中一次耦合关系,使得众子类耦合关系得到了解耦。从uml 也可以看的出来,父类间是紧耦合的,而子类中却是松耦合的。
举例
以改变北京时间,而其它时间也会随之而改变为例 ,程序如下:
是讲有一个目标,众多个观察者去“观察”目标。目标是目标抽象类的一个派生类,观察者是观察者抽象类的一个派生类。当目标类的数据改变,所有对应的观察者对应去更新自己的状态。注意观察者处于被动地位,被观察者处理主动地位。
应用场景
比如有一个世界时钟程序,有多个图形时钟去显示比如北京时区,巴黎时区,等等。如果设置一个北京时间,那么其他时钟图形都需要更新(加上或者减去时差值)。典型的图形界面设计随处可见,一个温度程序,在温度湿度等条件改变时,要更新多种显示图形来呈现。
UML图示
原本是子类间进行耦合,把子类间的耦合提升到父类中去,这样父类中一次耦合关系,使得众子类耦合关系得到了解耦。从uml 也可以看的出来,父类间是紧耦合的,而子类中却是松耦合的。
举例
以改变北京时间,而其它时间也会随之而改变为例 ,程序如下:
#include <iostream> #include <list> #include <algorithm> using namespace std; class Subject; class Observer //观察者 { public: virtual void update(Subject * subject) = 0; int _hour; int _min; int _sec; Subject * _subject; }; class Subject //被观察者 { public: void addRegister(Observer * observer) // 观察者注册 { observerList.push_back(observer); } void delRegister(Observer * observer) // 观察者取消 { observerList.erase(find(observerList.begin(),observerList.end(),observer)); } void notify() { list<Observer*>::iterator itr; for(itr = observerList.begin(); itr != observerList.end(); ++itr) { (*itr)->update(this); } } int _hour; int _min; int _sec; list<Observer*> observerList; //注册后的观察者集合 }; class ChinaClock:public Subject //被观察者子类 北京时间 { public: void set(int hour, int min, int sec) { cout<<"China clock is set"<<endl; _hour = hour; _min = min; _sec = sec; notify(); //被观察者发出通知 } }; class AmericaClock:public Observer //观察者子类 美国时间 { public: AmericaClock(Subject * subject) { _subject = subject; _subject->addRegister(this); } void update(Subject * subject) { _hour = subject->_hour; _min = subject->_min; _sec = subject->_sec; dis(); } void dis() { cout<<"America clock is set"<<endl; cout<<"hour:"<<_hour<<"min:"<<_min<<"sec:"<<_sec<<endl; } }; class LondenClock:public Observer //观察者子类 英国时间 { public: LondenClock(Subject * subject) { _subject = subject; _subject->addRegister(this); } void update(Subject * subject) { _hour = subject->_hour; _min = subject->_min; _sec = subject->_sec; dis(); } void dis() { cout<<"Londen clock is set"<<endl; cout<<"hour:"<<_hour<<"min:"<<_min<<"sec:"<<_sec<<endl; } }; class JapanClock:public Observer //观察者子类 日本时间 { public: JapanClock(Subject * subject) { _subject = subject; _subject->addRegister(this); } void update(Subject * subject) { _hour = subject->_hour; _min = subject->_min; _sec = subject->_sec; dis(); } void dis() { cout<<"Japan clock is set"<<endl; cout<<"hour:"<<_hour<<"min:"<<_min<<"sec:"<<_sec<<endl; } }; int main() { ChinaClock *cc = new ChinaClock; //创建北京时间被观察对象 AmericaClock *ac = new AmericaClock(cc); //创建美国时间观察对象 LondenClock *lc = new LondenClock(cc); //创建英国时间观察对象 JapanClock *jc = new JapanClock(cc); //创建日本时间观察对象 cc->set(1,2,3); //改变被观察北京时间 cout<<"-------------"<<endl; cc->delRegister(jc); //移除日本时间观察者 cc->set(6,7,8); //再次改变被观察者时间 return 0; }
相关文章推荐
- 【转载】c++之类的基本操作(c++ primer 的读书笔记 ,类对象, 类用户, 类成员的含义)
- VS开发】C中调用C++文件中定义的function函数
- 学习笔记——关于指向常量指针的解引用的发现
- C++直接初始化和复制初始化2
- C++直接初始化和复制初始化1
- C语言之字符串
- 【C语言提高24】二级指针做输入的第一种内存模型:数组指针
- 解决iOS报错libc++abi.dylib handler threw exception
- 【C语言提高23】二级指针做输出的内存模型
- c语言中static用法总结
- VS2008 C++ 调用托管C++dll 当前不会命中断点,没有与此关联的代码
- C++ (Bug)--调 C文件,报错 xxxx.0 not fountt, x86
- C++ Timer定时器
- Vector c++ 的基本操作 矢量 *_* !
- printf 格式化输出符号详细说明
- C++终极复习篇(五)----STL标准模板库
- MFC 学习之 鼠标移动到Toolbar按钮上显示提示信息(tooltip),状态栏也随之改变
- c语言学习
- C++中头文件的概念与基本编写方法
- C++ string 大小写互转(八~二)