设计模式——观察者模式
概念
Observer模式也称为发布-订阅(publish-subscribe),定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。当一个对象发生了变化,关注它的对象就会得到通知;这种交互也称为发布-订阅(publish-subscribe)。目标是通知的发布者,它发出通知时并不需要知道谁是它的观察者。常用于解耦事件的观察和事件最终的处理方式。
解决的问题
Observer模式要解决的问题为:建立一个一(Subject)对多( Observer )的依赖关系,并且做到当“一”变化的时候,依赖这个“一” 的多也能够同步改变。
例子:对同一组数据进行统计分析时候,我们希望能够提供多种形式的表示(例如以表格进行统计显示、柱状图统计显示、百分比统计显示等)。 这些表示都依赖于同一组数据,我们当然需要当数据改变的时候,所有的统计的显示都能够同时改变。
uml类图
demo
#include<iostream>
#include<set>
using namespace std;
class Observer {
public:
virtual void update(int data) = 0; /*纯虚函数*/
};
class ConcreteObserverA : public Observer {
public:
virtual void update(int data) {
_data = data;
cout << "ConcreteObserverA updates data " << _data << endl;
}
private:
int _data;
};
class ConcreteObserverB : public Observer {
public:
virtual void update(int data) {
_data = data;
cout << "ConcreteObserverB updates data " << _data << endl;
}
private:
int _data;
};
class ConcreteObserverC : public Observer {
public:
virtual void update(int data) {
_data = data;
cout << "ConcreteObserverC updates data " << _data << endl;
}
private:
int _data;
};
class Subject {
public:
Subject () = default;
virtual ~Subject() {};
/*给每个主题增加观察者对象及对象感兴趣的事件*/
virtual void addObserver(Observer* ob) {
auto it = _observerPtrSet.find(ob);
if (it == _observerPtrSet.end()) {
_observerPtrSet.insert(ob);
}
}
/*观察者取消订阅*/
virtual void delObserver(Observer* ob) {
auto it = _observerPtrSet.find(ob);
if (it != _observerPtrSet.end()) {
_observerPtrSet.erase(it);
}
}
/*给订阅了该事件的观察者发送推送消息*/
virtual void disPatch(int data) {
for (auto &ob :_observerPtrSet) {
ob ->update(data);
}
}
private:
set<Observer*> _observerPtrSet;
};
class ConcreteSubject : public Subject {
};
int main() {
Observer* optr1 = new ConcreteObserverA();
Observer* optr2 = new ConcreteObserverB();
Observer* optr3 = new ConcreteObserverC();
Subject sub;
sub.addObserver(optr1);
sub.addObserver(optr2);
sub.addObserver(optr3);
sub.disPatch(3);
sub.disPatch(4);
}