观察者模式通常的叫法叫做订阅-发布模式,类似于报刊杂志的订阅,观察者和被观察者就是读者和邮局的关系,读者先要在邮局订阅想要的报刊,当报刊发行时,邮局会将报刊邮寄到读者家里。观察者(Observer)和被观察者(Listener)也是这种关系,Observer将自己attach到Listener中,当Listener触发时Notify所有Observer.

作用

在观察者模式中,被观察者维护观察者对象的集合,当被观察者对象变化时,它会通知观察者。观察者模式主要是用于解决对象之间一对多的关系。

类视图

实现

class Observer
{
public:
virtual ~Observer() {};
virtual void Update(const std::string &msg)= 0;
protected:
Observer(){};
}; class Listener
{
public:
virtual ~Listener() {};
void attach(Observer* obsvr)
{
m_observers.push_back(obsvr);
}
void remove(Observer* obsvr)
{
m_observers.remove(obsvr);
}
void notify(const std::string &msg)
{
list<Observer*>::iterator iter = m_observers.begin();
for(; iter != m_observers.end(); iter++)
(*iter)->Update(msg);
}
private:
list<Observer* > m_observers; //观察者链表
}; class logRunner : public Listener
{
public:
virtual ~logRunner(){};
void addmsg(const std::string &msg)
{
nofity(msg);
}
} class logGui : public Observer
{
public:
virtual ~Observer(){};
void Update(const std::string &msg)
{
cout<< "Gui log show : "<< msg <<endl;
}
} class logFile : public Observer
{
public:
virtual ~Observer(){};
void Update(const std::string &msg)
{
cout<< "file log write : "<< msg <<endl;
}
} class logDebug : public Observer
{
public:
virtual ~Observer(){};
void Update(const std::string &msg)
{
cout<< "Debug log out : "<< msg <<endl;
}
} class logDataBase : public Observer
{
public:
virtual ~Observer(){};
void Update(const std::string &msg)
{
cout<< "DataBase log in : "<< msg <<endl;
}
} int main()
{
logRunner Runner;
logGui gGui;
logFile gFile;
logDebug gDebug;
logDataBase gDataBase; Runner.attach(&gGui);
Runner.attach(&gFile);
Runner.attach(&gDebug);
Runner.attach(&gDataBase); Runner.addmsg("app is setup");
}

Observer中update一般为纯虚,通过子类各自实现,这里只是保证调用的接口一致,Listener中的attach、remove、notify一般建议不进行虚化,子类不用关心其内部的聚合内容,通过调用notify实现消息分发即可。当然也可以虚化,将这一系列的操作放到子类进行实现。

调用者应该注意在多线程环境中的使用环境,做好数据的同步工作。

应用场景

  1. 当一个对象改变需要通知到其他对象,而我们不确定由多少对象需要通知时;
  2. 当一个对象必须通知其他对象,而不需要知道对象是什么实现时;
  3. 对于一堆对象,包含同样的状态或同样的数据,通过同一个条件进行更新时。

设计模式之观察者模式(Observer)的更多相关文章

  1. 乐在其中设计模式(C#) - 观察者模式(Observer Pattern)

    原文:乐在其中设计模式(C#) - 观察者模式(Observer Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 观察者模式(Observer Pattern) 作者:weba ...

  2. 8.5 GOF设计模式四: 观察者模式Observer

    GOF设计模式四: 观察者模式Observer  现实中遇到的问题  当有许多不同的客户都对同一数据源感兴趣,对相同的数据有不同的处理方式,该如 何解决?5.1 定义: 观察者模式  观察者模式 ...

  3. 人人都会设计模式:观察者模式--Observer

    https://segmentfault.com/a/1190000012295887 观察者模式是抽像通知者和观察者,达到具体通知者跟具体观察者没有偶合.能达到不管是切换通知者,或者是切换观察者,都 ...

  4. 二十四种设计模式:观察者模式(Observer Pattern)

    观察者模式(Observer Pattern) 介绍定义对象间的一种一对多的依赖关系,以便当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并自动刷新. 示例有一个Message实体类,某些对象 ...

  5. [设计模式] 19 观察者模式 Observer Pattern

    在GOF的<设计模式:可复用面向对象软件的基础>一书中对观察者模式是这样说的:定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新.当一个 ...

  6. c#设计模式之观察者模式(Observer Pattern)

    场景出发 一个月高风黑的晚上,突然传来了尖锐的猫叫,宁静被彻底打破,狗开始吠了,大人醒了,婴儿哭了,小偷跑了 这个过程,如果用面向对象语言来描述,简单莫过于下: public class Cat { ...

  7. JAVA设计模式之观察者模式 - Observer

    有趣的事情发生时,可千万别错过了!有一个模式可以帮你的对象知悉现况,不会错过该对象感兴趣的事.对象甚至在运行时可决定是否要继续被通知.有了观察者,你将会消息灵通. 介绍 观察者模式的定义: 在对象之间 ...

  8. 设计模式之观察者模式(Observer pattern)

    最近参加了一次面试,其中笔试题有一道编程题,在更换掉试题的描述场景后,大意如下: 上课铃声响起,学生A/B/C/D进入教室:下课铃声响起,学生A/B/C/D离开教室. 要求使用设计模式的思想完成铃与学 ...

  9. 设计模式之观察者模式(Observer)

    观察者模式原理:当有新的消息产生时发送给观察者,和中介者模式的不同地方是中介者模式强调中介的作用以及中介双方的交互,观察者模式是主动调用观察者成员函数进行消息发送. 代码如下: #include &l ...

  10. 设计模式九: 观察者模式(Observer Pattern)

    简介 观察者属于行为型模式的一种, 又叫发布-订阅模式. 如果一个对象的状态发生改变,依赖他的对象都将发生变化, 那么这种情况就适合使用观察者模式. 它包含两个术语,主题(Subject),观察者(O ...

随机推荐

  1. jupyter Notebook环境搭建

    1.什么是jupyter notebook jupyter notebook是一种 Web 应用,能让用户将说明文本.数学方程.代码和可视化内容全部组合到一个易于共享的文档中.它可以直接在代码旁写出叙 ...

  2. ajax 删除数据无刷新

    //html页面 <!doctype html><head> <title></title> <meta http-equiv="Con ...

  3. 3 week work—Position

    源代码部分: (1)httm部分: <!DOCTYPE html> <html lang="en"> <head> <meta chars ...

  4. 4.ASP.NET MVC 5.0 视图之模型绑定

    大家好,这篇文章,我将向大家介绍ASP.NET MVC的模型视图绑定,ASP.MVC的模型绑定分为两种:一种是动态绑定[Dynamic Binding];还有一种就是强类型绑定[Strongly ty ...

  5. layui 富文本 图片上传 后端PHP接口

    <!DOCTYPE html> <html> <head> <link rel="stylesheet" type="text/ ...

  6. 完善版封装canvas分享组件

    import regeneratorRuntime from "../../../lib/regenerator-runtime/runtime"; let ctx = false ...

  7. 美团2018年CodeM大赛-初赛B轮 C题低位值

    试题链接:https://www.nowcoder.com/acm/contest/151/C 定义lowbit(x) =x&(-x),即2^(p-1) (其中p为x的二进制表示中,从右向左数 ...

  8. linux中ftp的安装过程记录[运维篇]

    安装FTP的全过程记录,对于相同情况希望有所帮助.[centOS] 1.查询本机是否安装vsftpd: rpm -qa |grep vsftpd : 2.安装ftp服务 yum install vsf ...

  9. Spring boot 使用 configuration 获取的属性为 null

    1. 未设置 getter(),setter()方法,导致属性值注入失败: 2. spring 未扫描到该组件,在其他类中注入该对象失败,可在配置类添加 @configuration 或者 @comp ...

  10. Calling Functions With Pointer Parameters

     参数类型是Constant Pointer 也就是 UnsafePointer<Type> 可以传入的类型: UnsafePointer<Type>/UnsafeMutab ...