设计模式之职责链模式(Chain
of Responsibility)摘录
Chain of Responsibility:
(1)、意图:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为支。
(2)、适用性:
A、有多个的对象可以处理一个请求,哪个对象处理该请求运行时刻自动确定。
B、你想在不明确指定接收者的情况下,向多个对象中的一个提交一个请求。
C、可处理一个请求的对象集合应被动态指定。
(3)、优缺点:
A、降低耦合度:该模式使得一个对象无需知道是其它哪一个对象处理其请求。对象仅需知道该请求会被”正确”地处理。接收者和发送者都没有对方的明确的信息,且链中的对象不需知道链的结构。结果是,职责链可简化对象的相互连接。它们仅需保持一个指向其后继者的引用,而不需保持它所有的候选接收者的引用。
B、增强了给对象指派职责(Responsibility)的灵活性:当在对象中分派职责时,职责链给你更多的灵活性。你可以通过在运行时刻对该链进行动态的增加或修改来增加或改变处理一个请求的那些职责。你可以将这种机制与静态的特例化处理对象的继承机制结合起来使用。
C、不保证被接收:既然一个请求没有明确的接收者,那么就不能保证它一定会被处理------该请求可能一直到链的末端都得不到处理。一个请求也可能因为链没有被正确配置而得不到处理。
(4)、相关模式:职责链常与Composite一起使用。这种情况下,一个构件的父构件可作为它的后继。
(5)、Chain ofResponsibility模式中ConcreteHandler将自己的后继对象(向下传递消息的对象)记录在自己的后继表中,当一个请求到来时,ConcreteHandler会先检查看自己有没有匹配的处理程序,如果有就自己处理,否则传递给它的后继。Chain
of Responsibility模式的最大的一个优点就是给系统降低了耦合性,请求的发送者完全不必知道该请求会被哪个应答对象处理,极大地降低了系统的耦合性。
示例代码1:
#include <iostream> #include <string> #include <vector> using namespace std; //请求 class Request { public: string m_strContent; int m_nNumber; }; //管理者 class Manager { protected: Manager* manager; string name; public: Manager(string temp) { name = temp; } void SetSuccessor(Manager* temp) { manager = temp; } virtual void GetRequest(Request* request) = 0; }; //经理 class CommonManager : public Manager { public: CommonManager(string strTemp) : Manager(strTemp) {} virtual void GetRequest(Request* request) { if (request->m_nNumber >= 0 && request->m_nNumber < 10) cout<<name<<"处理了"<<request->m_nNumber<<"个请求"<<endl; else manager->GetRequest(request); } }; //总监 class MajorDomo : public Manager { public: MajorDomo(string name) : Manager(name) {} virtual void GetRequest(Request* request) { if (request->m_nNumber >= 10) cout<<name<<"处理了"<<request->m_nNumber<<"个请求"<<endl; } }; //客户端 int main() { Manager* common = new CommonManager("张经理"); Manager* major = new MajorDomo("李总监"); common->SetSuccessor(major); Request* req = new Request(); req->m_nNumber = 33; common->GetRequest(req); req->m_nNumber = 3; common->GetRequest(req); /*result 李总监处理了33个请求 张经理处理了3个请求 */ return 0; } |
示例代码2:
Handle.h:
#ifndef _HANDLE_H_ #define _HANDLE_H_ class Handle { public: virtual ~Handle(); virtual void HandleRequest() = 0; void SetSuccessor(Handle* succ); Handle* GetSuccessor(); protected: Handle(); Handle(Handle* succ); private: Handle* _succ; }; class ConcreteHandleA : public Handle { public: ConcreteHandleA(); ~ConcreteHandleA(); ConcreteHandleA(Handle* succ); void HandleRequest(); protected: private: }; class ConcreteHandleB : public Handle { public: ConcreteHandleB(); ~ConcreteHandleB(); ConcreteHandleB(Handle* succ); void HandleRequest(); protected: private: }; #endif//~_HANDLE_H_ |
Handle.cpp:
#include "Handle.h" #include <iostream> using namespace std; Handle::Handle() { _succ = 0; } Handle::~Handle() { delete _succ; } Handle::Handle(Handle* succ) { this->_succ = succ; } void Handle::SetSuccessor(Handle* succ) { _succ = succ; } Handle* Handle::GetSuccessor() { return _succ; } void Handle::HandleRequest() { } ConcreteHandleA::ConcreteHandleA() { } ConcreteHandleA::ConcreteHandleA(Handle* succ) : Handle(succ) { } ConcreteHandleA::~ConcreteHandleA() { } void ConcreteHandleA::HandleRequest() { if (this->GetSuccessor() != 0) { cout<<"ConcreteHandleA 我把处理权给后继节点 ..."<<endl; this->GetSuccessor()->HandleRequest(); } else cout<<"ConcreteHandleA 没有后继了, 我必须自己处理 ..."<<endl; } ConcreteHandleB::ConcreteHandleB() { } ConcreteHandleB::ConcreteHandleB(Handle* succ) : Handle(succ) { } ConcreteHandleB::~ConcreteHandleB() { } void ConcreteHandleB::HandleRequest() { if (this->GetSuccessor() != 0) { cout<<"ConcreteHandleB 我把处理权给后继节点 ..."<<endl; this->GetSuccessor()->HandleRequest(); } else cout<<"ConcreteHandleB 没有后继了,我必须自己处理 ..."<<endl; } |
main.cpp:
#include "Handle.h" #include <iostream> using namespace std; int main() { Handle* h1 = new ConcreteHandleA(); Handle* h2 = new ConcreteHandleB(); h1->SetSuccessor(h2); h1->HandleRequest(); /*result ConcreteHandleA 我把处理权给后继节点 ... ConcreteHandleB 没有后继了,我必须自己处理 ... */ return 0; } |
职责链模式结构图:
设计模式之迭代器模式(Iterator)摘录
Iterator:(1)、意图:提供一种方法顺序访问一个聚合对象中各个元素,而又不暴露该对象的内部表示。为遍历不同的聚集结构提供如开始、下一个、是否结束,当前一项等统一接口。
(2)、适用性:A、访问一个聚合对象的内容而无需暴露它的内部表示。B、支持对聚合对象的多种遍历。C、为遍历不同的聚合结构提供一个统一的接口(即支持多态迭代)。
(3)、优缺点:
A、它支持以不同的方式遍历一个聚合:复杂的聚合可用多种方式进行遍历。例如,代码生成和语义检查要遍历语法分析树。代码生成可以按中序或者按前序来遍历语法分析树。迭代器使得改变遍历算法变得很容易:仅需用一个不同的迭代器的实例代替原先的实例即可。你也可以自己定义迭代器的子类以支持新的遍历。
B、迭代器简化了聚合的接口:有了迭代器的遍历接口,聚合本身就不再需要类似的遍历接口了。这样就简化了聚合的接口。
C、在同一个聚合上可以有多个遍历:每个迭代器保持它自己的遍历状态。因此你可以同时进行多个遍历。
(4)、相关模式:
A、Composite:迭代器常被应用到像复合这样的递归结构上。
B、Factory Method:多态迭代器靠Factory Method来例化适当的迭代器子类。
C、Memento:常与迭代器模式一起使用。迭代器可使用一个memento来捕获一个迭代的状态。迭代器在其内部存储memento。
示例代码:
Aggregate.h:
#ifndef _AGGREGATE_H_ #define _AGGREGATE_H_ class Iterator; typedef int Object; class Interator; class Aggregate { public: virtual ~Aggregate(); virtual Iterator* CreateIterator() = 0; virtual Object GetItem(int idx) = 0; virtual int GetSize() = 0; protected: Aggregate(); private: }; class ConcreteAggregate : public Aggregate { public: enum {SIZE = 3}; ConcreteAggregate(); ~ConcreteAggregate(); Iterator* CreateIterator(); Object GetItem(int idx); int GetSize(); protected: private: Object _objs[SIZE]; };#endif//~_AGGREGATE_H_ |
Aggregate.cpp:
#include "Aggregate.h" #include "Iterator.h" #include <iostream> using namespace std; Aggregate::Aggregate() { } Aggregate::~Aggregate() { } ConcreteAggregate::ConcreteAggregate() { for (int i = 0; i < SIZE; i ++) _objs[i] = i; } ConcreteAggregate::~ConcreteAggregate() { } Iterator* ConcreteAggregate::CreateIterator() { return new ConcreteIterator(this); } Object ConcreteAggregate::GetItem(int idx) { if (idx < this->GetSize()) return _objs[idx]; else return -1; } int ConcreteAggregate::GetSize() { return SIZE; } |
Iterator.h:
#ifndef _ITERATOR_H_ #define _ITERATOR_H_ class Aggregate; typedef int Object; class Iterator { public: virtual ~Iterator(); virtual void First() = 0; virtual void Next() = 0; virtual bool IsDone() = 0; virtual Object CurrentItem() = 0; protected: Iterator(); private: }; class ConcreteIterator : public Iterator { public: ConcreteIterator(Aggregate* ag, int idx = 0); ~ConcreteIterator(); void First(); void Next(); bool IsDone(); Object CurrentItem(); protected: private: Aggregate* _ag; int _idx; };#endif//~_ITERATOR_H_ |
Iterator.cpp:
#include "Iterator.h" #include "Aggregate.h" #include <iostream> using namespace std; Iterator::Iterator() { } Iterator::~Iterator() { } ConcreteIterator::ConcreteIterator(Aggregate* ag, int idx) { this->_ag = ag; this->_idx = idx; } ConcreteIterator::~ConcreteIterator() { } Object ConcreteIterator::CurrentItem() { return _ag->GetItem(_idx); } void ConcreteIterator::First() { _idx = 0; } void ConcreteIterator::Next() { if (_idx < _ag->GetSize()) _idx ++; } bool ConcreteIterator::IsDone() { return (_idx == _ag->GetSize()); } |
main.cpp:
#include "Iterator.h" #include "Aggregate.h" #include <iostream> using namespace std; int main() { Aggregate* ag = new ConcreteAggregate(); Iterator* it = new ConcreteIterator(ag); for (; !(it->IsDone()); it->Next()) cout<<it->CurrentItem()<<endl; /*result 0 1 2 */ return 0; } |
迭代器模式结构图:
|