標籤:style blog http color os io 2014 ar
責任鏈模式是一種軟體設計模式,它包含了一些命令對象和一系列的處理對象。每一個處理對象決定它能處理哪些命令對象,它也知道如何將它不能處理的命令對象傳遞給該鏈中的下一個處理對象。該模式還描述了往該處理鏈的末尾添加新的處理對象的方法。責任鏈模式的UML圖如下:
下面是一個用C++描述的責任鏈模式的例子:
#include <iostream>#include <string>using namespace std;// 抽象類別,定義處理請求的介面class Logger {public:static const int DEBUG = 1;static const int NOTICE = 2;static const int ERR = 3;// 設定責任鏈下一個成員void setNext(Logger *log){next = log;}// 根據優先順序決定處理訊息或傳遞給下一個處理者void message(string msg, int priority){if (priority <= mask)writeMessage(msg);else if (next != NULL)next->message(msg, priority);}protected:int mask;// The next element in the chain of responsibilityLogger *next;virtual void writeMessage(string msg) = 0;};// 具體處理者class StdoutLogger : public Logger {public:StdoutLogger(int m){mask = m;}protected:void writeMessage(string msg){cout << "Writting to stdout: " << msg << endl;}};// 具體處理者class EmailLogger : public Logger {public:EmailLogger(int m){mask = m;}protected:void writeMessage(string msg){cout << "Sending via email: " << msg << endl;}};// 具體處理者class StderrLogger : public Logger{public:StderrLogger(int m){mask = m;}protected:void writeMessage(string msg){cout << "Sending to stderr: " << msg << endl;}};int main(){Logger *log1 = new StdoutLogger(Logger::DEBUG);Logger *log2 = new EmailLogger(Logger::NOTICE);Logger *log3 = new StderrLogger(Logger::ERR);// Build the chain of responsibilitylog1->setNext(log2);log2->setNext(log3);// Handled by StdoutLoggerlog1->message("Hello world.", Logger::DEBUG);// Handled by EmailLoggerlog1->message("Sending a Email.", Logger::NOTICE);// Handled by StderrLoggerlog1->message("An error has occurred.", Logger::ERR);system("pause");return 0;}
運行結果:
上面的例子中,我們建立了三個處理訊息的對象,根據內容的優先順序分別把內容輸出到標準輸出、郵件、標準錯誤。當一個處理對象無法處理這個等級的內容時,將自動傳遞給責任鏈中的下一個處理者處理。也就是說,當客戶提交一個請求時,請求是沿著責任鏈傳遞直至一個具體的負責處理內容的對象。責任鏈的優點在於,處理內容的對象是通過鏈表串連起來的,增加或修改責任鏈是非常方便靈活的。實際上,責任鏈模式就是把if-else結構改成了鏈表結構來處理不同的訊息,大大降低了代碼的耦合度。
參考:
維基百科
《大話設計模式》第24章