您的位置:首页 > 其它

Observer

2013-10-29 11:00 162 查看
// 观察者(Observer )模式又名发布-订阅(Publish/Subscribe)模式。GOF 给观察者模

//式如下定义:定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依

//赖于它的对象都得到通知并被自动更新。

//观察者模式的起源我觉得 应该是在 GUI 和业务数据的处理上

//观察者模式的组成部分。

//1) 抽象目标角色(Subject ):目标角色知道它的观察者,可以有任意多个观察者观察同一

// 个目标。并且提供注册和删除观察者对象的接口。目标角色往往由抽象类或者接口来实

// 现。

//2) 抽象观察者角色(Observer ):为那些在目标发生改变时需要获得通知的对象定义一个

// 更新接口。抽象观察者角色主要由抽象类或者接口来实现。

//3) 具体目标角色(Concrete Subject ):将有关状态存入各个Concrete Observer 对象。当

// 它的状态发生改变时, 向它的各个观察者发出通知。

//4) 具体观察者角色(Concrete Observer ):存储有关状态,这些状态应与目标的状态保持

// 一致。实现Observer 的更新接口以使自身状态与目标的状态保持一致。在本角色内也

// 可以维护一个指向Concrete Subject 对象的引用。

// 放上观察者模式的类图,这样能将关系清晰的表达出来。

//

//使用情况

// GOF 给出了以下使用观察者模式的情况:

// 1) 当一个抽象模型有两个方面, 其中一个方面依赖于另一方面。将这二者封装在独立

// 的对象中以使它们可以各自独立地改变和复用。

// 2) 当对一个对象的改变需要同时改变其它对象, 而不知道具体有多少对象有待改变。

// 3) 当一个对象必须通知其它对象,而它又不能假定其它对象是谁。换言之, 你不希望

// 这些对象是紧密耦合的。

#include <list>

#include <string>

//Observer模式,就是建立一种机制,使多个对象依赖于某个特定对象,当这个特定的对象改变时,能通知到依赖它的所有对象作出反应。

//类A(观察目标)中包含一个 节点为观察类的链表 包含一个通知状态函数 。 具体化类A可以修改状态 状态变更后调用通知观察者调用自身的update做出反馈

using namespace std;

typedef string State; //与宏类似

class Observer;

class Subject //观察目标对象

{

public:

virtual ~Subject();

//添加 删除观察者

virtual void Attach(Observer* obv) {_obvs->push_front(obv);}//贴上 系 附上

virtual void Detach(Observer* obv){if (obv != NULL) _obvs->remove(obv);}//拆卸, 使分开, 使分离

//通知观察者

virtual void Notify()//通知

{

list<Observer*>::iterator it;

it = _obvs->begin();

for (;it != _obvs->end();it++)

{ //关于模板和iterator的用法

(*it)->Update(this); //更新对目标的观察结果

}

}

virtual void SetState(const State& st) = 0;

virtual State GetState() = 0;

protected:

Subject()

{ //****在模板的使用之前一定要new,创建

_obvs = new list<Observer*>;

}

private:

list<Observer* >* _obvs;

};

class ConcreteSubject:public Subject

{

public:

ConcreteSubject(){_st = '\0';}

~ConcreteSubject();

State GetState(){return _st;}

void SetState(const State& st){_st = st;}

protected:

private:

State _st;

};

class Observer

{

public:

virtual ~Observer(){_st = '\0';}

virtual void Update(Subject* sub) = 0;

virtual void PrintInfo() = 0;//反馈观察结果

protected:

Observer();

State _st; //用来记录观察的到的状态

private:

};

class ConcreteObserverA:public Observer

{

public:

virtual Subject* GetSubject(){return _sub;}//得到观察目标

ConcreteObserverA(Subject* sub)

{

_sub = sub;

_sub->Attach(this);

}

virtual ~ConcreteObserverA()

{

_sub->Detach(this);

if (_sub != 0)

delete _sub;

}

//传入Subject作为参数,这样可以让一个View属于多个的Subject。

void Update(Subject* sub)

{

_st = sub->GetState();

PrintInfo();

}

void PrintInfo()

{

cout<<"ConcreteObserverA observer.... "<<_sub->GetState()<<endl;

}

protected:

private:

Subject* _sub;

};

class ConcreteObserverB:public Observer

{

public:

virtual Subject* GetSubject(){return _sub;}

ConcreteObserverB(Subject* sub)

{

_sub = sub;

_sub->Attach(this);

}

virtual ~ConcreteObserverB()

{

_sub->Detach(this);

if (_sub != 0)

delete _sub;

}

//传入Subject作为参数,这样可以让一个View属于多个的Subject。

void Update(Subject* sub)

{

_st = sub->GetState();

PrintInfo();

}

void PrintInfo()

{

cout<<"ConcreteObserverB observer.... "<<_sub->GetState()<<endl;

}

protected:

private:

Subject* _sub;

};

void Observe_test()

{

ConcreteSubject* sub = new ConcreteSubject();//创建观察目标

Observer* o1 = new ConcreteObserverA(sub);//创建一个以sub为观察目标的观察者

Observer* o2 = new ConcreteObserverB(sub);

sub->SetState("old");//每次状态改变时 目标对象都会通知观察者

sub->Notify();

sub->SetState("new");

sub->Notify();

;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: