观察者模式

来源:互联网 发布:唐筛标准年龄风险数据 编辑:程序博客网 时间:2024/06/06 05:23

1.定义

定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。


2.UML图

角色:
主题(Subject):一个接口,规定了具体主题需要实现的方法。
观察者(Observer):也是一个接口,规定了具体观察者用来更新数据的方法。
具体主题:实现主题接口的一个实例,比如本例中的“就业通知中心”;里面会维护一个具体观察者的集合。本文使用STL中的list。
具体观察者:实现观察者的一个实例,会包含存放主题的引用或者指针。

3.代码实现

#include <iostream>#include <list>using namespace std;#define SAFE_RELEASE(_p){ if((_p)){ delete (_p); (_p) = NULL;} }class Blog;//观察者基类class Observer{public:Observer() {}virtual ~Observer() {}virtual void Update(int idBlog) = 0;virtual void Collect(Blog* blog) = 0;};//博客基类class Blog{public:Blog(int idBlog) : m_idBlog(idBlog) {}virtual ~Blog() {}void Attach(Observer *observer) { m_observers.push_back(observer); }//添加观察者void Remove(Observer *observer) { m_observers.remove(observer); }//移除观察者//通知观察者void Notify(){list<Observer*>::iterator iter = m_observers.begin();for (;iter != m_observers.end();iter++) {(*iter)->Update(m_idBlog);}}virtual void SetStatus(string status) { m_status = status; }//设置状态virtual string GetStatus() { return m_status; }//获得状态int GetBlogID() { return m_idBlog; }protected:intm_idBlog;//博客IDstringm_status;//状态private:list<Observer*>m_observers;//观察者链表};//具体观察者class ObserverBlog : public Observer{public:ObserverBlog(string name) : m_name(name){}~ObserverBlog() {}//更新指定的博客virtual void Update(int idBlog){list<Blog*>::iterator iter = m_blogList.begin();for (;iter != m_blogList.end();iter++) {Blog* blog = *iter;if (idBlog == blog->GetBlogID()) {string status = blog->GetStatus();cout<<m_name.c_str()<<"-------"<<status.c_str()<<endl;}}}virtual void Collect(Blog* blog) {m_blogList.push_back(blog);}private:stringm_name;//观察者名称list<Blog*>m_blogList;//观察者收藏的博客列表,可以收藏多个博客};//具体博客类class BlogCSDN : public Blog{public:BlogCSDN(int idBlog, string name) : Blog(idBlog), m_name(name) {}~BlogCSDN() {}virtual void SetStatus(string s) { m_status.append("CSDN通知 : ").append(m_name).append(s); } //具体设置状态信息virtual string GetStatus() { return m_status; }private:stringm_name;//博主名称};int main(){Blog *blog123 = new BlogCSDN(123, "blog123");Blog *blog456 = new BlogCSDN(456, "blog456");Observer *observer1 = new ObserverBlog("tutupig");//以上两行可以看做:一个观看者看博客文章,所以定义观看者类和博客文章类observer1->Collect(blog123);//观看者收藏了该博客observer1->Collect(blog456);blog123->Attach(observer1);//将观看者添加到观看者列表,如果博客有更新,通知观看者列表//更改博客状态,并通知观看者,博客已经更新blog123->SetStatus("发表设计模式C++实现(15)——观察者模式");blog123->Notify();SAFE_RELEASE(blog123);SAFE_RELEASE(blog456);SAFE_RELEASE(observer1);return 0;}