行为型模式
18)观察者模式
本文参考:
https://www.cnblogs.com/yangjj08/p/10533250.html
https://www.cnblogs.com/mfrbuaa/p/4364678.html
观察者模式定义了一种一对多的依赖关系,让多个观察者同时监听某一主题对象,当主题对象变化时,会通知所有的观察者。
观察者模式包含如下角色:
第一种,观察者,抽象类,也就是被迫发生变化的类。
第二种,被观察者,抽象类,感知到变化、且主动通知的类。
观察者模式的作用是当一个状态变化时,会主动通知其它关联对象,自己主动刷新对象状态。实现观察者的时候需要注意,观察者和被观察者之间不能有直接的调用关系,这样就让观察者和被观察者产生了强烈的耦合,从根本上违反面向对象的设计原则。
观察者模式完美得将观察者和被观察的对象分开。比如,鼠标是被观察者,界面程序是观察者,当鼠标点击后,界面需要自己主动跳转到新的页面等。面对对象设计的一个原则是一个对象仅仅需要做好一件事。从而将观察者和被观察者解耦。
using namespace std;
//观察者
class Program{
public:
virtual void onMouseOnceClick() = 0;
};
class WebPage : public Program {
public:
void onMouseOnceClick() {
cout << "WebPage closing" << endl;
}
};
class MicrosoftOffice : public Program {
public:
void onMouseOnceClick() {
cout << "Office closing" << endl;
}
};
//被观察者,控件
class control {
public:
virtual void registerProgram(Program*) = 0; //注册与控件相关联的程序
virtual void removeProgram(Program*) = 0; //删除与控件相关联的程序
virtual void notify() = 0; //通知所有的程序
};
//单次点击鼠标
class OnceClickMouse : public control {
public:
void registerProgram(Program* p) {
m_programs.push_back(p);
}
void removeProgram(Program* p) {
vector<Program*>::iterator it;
for (it = m_programs.begin(); it != m_programs.end(); it++) {
if (*it == p) {
m_programs.erase(it);
break;
}
}
}
//通知观察者,做出必要的反应
void notify() {
vector<Program*>::iterator it;
for (it = m_programs.begin(); it != m_programs.end(); it++) {
(*it)->onMouseOnceClick();
}
}
private:
vector<Program*> m_programs;
};
int main() {
Program* webpage1 = new WebPage();
Program* office1 = new MicrosoftOffice();
control* mouseclick = new OnceClickMouse();
mouseclick->registerProgram(webpage1);
mouseclick->registerProgram(office1);
//鼠标点击后
mouseclick->notify();
}