1. 程式人生 > >我所理解的設計模式(C++實現)——責任鏈模式(Chain Of Responsibility Pattern)

我所理解的設計模式(C++實現)——責任鏈模式(Chain Of Responsibility Pattern)

概述:

     辛辛苦苦了工作了一年,終於可以加薪了,向主管提交了加薪申請,主管一看不得了,自己職權不夠,批不了,主管把申請上交總監,總監發現自己也批不了,申請到了總經理手中,總經理一看,小夥子口氣不小了,有膽識敢申請,先來談下心。預知後事如何,請看下回分解。

     這就是典型的職責鏈模式,請求的處理形成了一條鏈,直到有一個物件處理請求。責任鏈模式是一種物件的行為模式。在責任鏈模式裡,很多物件由每一個物件對其下家的引用而連線起來形成一條鏈。請求在這個鏈上傳遞,直到鏈上的某一個物件決定處理此請求。發出這個請求的客戶端並不知道鏈上的哪一個物件最終處理這個請求,這使得系統可以在不影響客戶端的情況下動態地重新組織鏈和分配責任。

類圖與例項:


抽象處理者(Handler)角色:定義出一個處理請求的介面。如果需要,介面可以定義出一個方法,以設定和返回對下家的引用。這個角色通常由一個抽象類或介面實現。

具體處理者(ConcreteHandler)角色:具體處理者接到請求後,可以選擇將請求處理掉,或者將請求傳給下家。由於具體處理者持有對下家的引用,因此,如果需要,具體處理者可以訪問下家。

樣例:

#include <iostream>
#include <string>
using namespace std;

// 請求
class Request
{
public:
	int m_nNumber;
};

// 管理者
class Manager
{
public:
	Manager(string temp) { name = temp; }
	void SetSuccessor(Manager* temp) { manager = temp; }
	virtual void GetRequest(Request* request) = 0;
protected:
	Manager* manager;
	string name;
};

// 經理
class CommonManager : public Manager
{
public:
	CommonManager(string strTemp) : Manager(strTemp) {}
	virtual void GetRequest(Request* request);
};

void CommonManager::GetRequest(Request* request)
{
	if (request->m_nNumber>=0 && request->m_nNumber<1000)
	{
		cout << name << " 處理了請求: " << request->m_nNumber << endl;
	}
	else
	{
		manager->GetRequest(request);
	}
}

// 總監
class Majordomo : public Manager
{
public:
	Majordomo(string strTemp) : Manager(strTemp) {}
	virtual void GetRequest(Request* request);
};

void Majordomo::GetRequest(Request* request)
{
	if (request->m_nNumber <= 5000)
	{
		cout << name << " 處理了請求: " << request->m_nNumber << endl;
	}else
	{
		manager->GetRequest(request);
	}
}

//總經理  
class GeneralManager: public Manager  
{  
public:  
	GeneralManager(string name):Manager(name) {}  
	virtual void GetRequest(Request* request)  //總經理可以處理所有請求  
	{ 		
		cout << name << " 處理了請求: " << request->m_nNumber << endl;		
	}  
};

int main(){

	Manager* common = new CommonManager("張經理");
	Manager* major = new Majordomo("李總監");
	GeneralManager* general  = new GeneralManager("趙總");
	common->SetSuccessor(major);
	major->SetSuccessor(general);
	Request* rq = new Request();

	rq->m_nNumber = 999;
	common->GetRequest(rq);
	
	rq->m_nNumber = 4999;
	common->GetRequest(rq);

	rq->m_nNumber = 6999;
	common->GetRequest(rq);

	delete rq;
	delete major;
	delete common;
	delete general;
	return 0;
}

要點與實現:

1.要注意的是:一個請求到鏈的最後可能也沒有處理,所以一定要配置得當.

2.責任鏈模式並不建立責任鏈。責任鏈的建立必須由系統的其它部分創建出來。

3.責任鏈模式降低了請求的傳送端和接收端之間的耦合,使多個物件都有機會處理這個請求。一個鏈可以是一條線,一個樹,也可以是一個環。如下圖所示,責任鏈是一個樹結構的一部分。


看到這裡的各位加薪申請都是general批...    :-))