請求的鏈式處理——職責鏈模式(二)

Liuwei-Sunny發表於2012-04-02

16.2 職責鏈模式概述

      很多情況下,在一個軟體系統中可以處理某個請求的物件不止一個,例如SCM系統中的採購單審批,主任、副董事長、董事長和董事會都可以處理採購單,他們可以構成一條處理採購單的鏈式結構,採購單沿著這條鏈進行傳遞,這條鏈就稱為職責鏈。職責鏈可以是一條直線、一個環或者一個樹形結構,最常見的職責鏈是直線型,即沿著一條單向的鏈來傳遞請求。鏈上的每一個物件都是請求處理者,職責鏈模式可以將請求的處理者組織成一條鏈,並讓請求沿著鏈傳遞,由鏈上的處理者對請求進行相應的處理,客戶端無須關心請求的處理細節以及請求的傳遞,只需將請求傳送到鏈上即可,實現請求傳送者和請求處理者解耦。

      職責鏈模式定義如下

職責鏈模式(Chain of Responsibility  Pattern):避免請求傳送者與接收者耦合在一起,讓多個物件都有可能接收請求,將這些物件連線成一條鏈,並且沿著這條鏈傳遞請求,直到有物件處理它為止。職責鏈模式是一種物件行為型模式。

      職責鏈模式結構的核心在於引入了一個抽象處理者。職責鏈模式結構如圖16-2所示:

 

      在職責鏈模式結構圖中包含如下幾個角色:

      ● Handler(抽象處理者):它定義了一個處理請求的介面,一般設計為抽象類,由於不同的具體處理者處理請求的方式不同,因此在其中定義了抽象請求處理方法。因為每一個處理者的下家還是一個處理者,因此在抽象處理者中定義了一個抽象處理者型別的物件(如結構圖中的successor),作為其對下家的引用。通過該引用,處理者可以連成一條鏈。

      ● ConcreteHandler(具體處理者):它是抽象處理者的子類,可以處理使用者請求,在具體處理者類中實現了抽象處理者中定義的抽象請求處理方法,在處理請求之前需要進行判斷,看是否有相應的處理許可權,如果可以處理請求就處理它,否則將請求轉發給後繼者;在具體處理者中可以訪問鏈中下一個物件,以便請求的轉發。

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

      職責鏈模式的核心在於抽象處理者類的設計,抽象處理者的典型程式碼如下所示:

abstract class Handler {
	//維持對下家的引用
protected Handler successor;
	
	public void setSuccessor(Handler successor) {
		this.successor=successor;
	}
	
	public abstract void handleRequest(String request);
}

       上述程式碼中,抽象處理者類定義了對下家的引用物件,以便將請求轉發給下家,該物件的訪問符可設為protected,在其子類中可以使用。在抽象處理者類中宣告瞭抽象的請求處理方法,具體實現交由子類完成。

        具體處理者是抽象處理者的子類,它具有兩大作用:第一是處理請求,不同的具體處理者以不同的形式實現抽象請求處理方法handleRequest()第二是轉發請求,如果該請求超出了當前處理者類的許可權,可以將該請求轉發給下家。具體處理者類的典型程式碼如下:

class ConcreteHandler extends Handler {
	public void handleRequest(String request) {
		if (請求滿足條件) {
			//處理請求
		}
		else {
			this.successor.handleRequest(request);  //轉發請求
		}
	}
}

       在具體處理類中通過對請求進行判斷可以做出相應的處理。

        需要注意的是職責鏈模式並不建立職責鏈,職責鏈的建立工作必須由系統的其他部分來完成,一般是在使用該職責鏈的客戶端中建立職責鏈職責鏈模式降低了請求的傳送端和接收端之間的耦合,使多個物件都有機會處理這個請求。 

 

思考

如何在客戶端建立一條職責鏈?

 【作者:劉偉  http://blog.csdn.net/lovelion

相關文章