c++ 中的观察者模式

观察者模式:
是讲有一个目标,众多个观察者去“观察”目标。目标是目标抽象类的一个派生类,观察者是观察者抽象类的一个派生类。当目标类的数据改变,所有对应的观察者对应去更新自己的状态。注意观察者处于被动地位,被观察者处理主动地位。
应用场景
比如有一个世界时钟程序,有多个图形时钟去显示比如北京时区,巴黎时区,等等。如果设置一个北京时间,那么其他时钟图形都需要更新(加上或者减去时差值)。典型的图形界面设计随处可见,一个温度程序,在温度湿度等条件改变时,要更新多种显示图形来呈现。
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;
}
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

developer_wgl

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值