使多個對象都有機會處理請求,從而避免請求的發送者和接收者之間的耦合關係。將這些對象連成一個鏈,並沿着鏈傳遞該請求,直到有一個對象處理它爲止。數組
職責鏈模式是一種行爲型模式,它包括命令對象以及一系列處理對象。每一個處理對象決定它可以處理哪些命令對象,將不能處理的命令對象傳遞至職責鏈中的下一個處理對象。app
想象一下公司的OA系統,提交請假單時系統會根據你的請假天數將申請單"交給"不一樣的人去審批,例如請假1-2天,只須要Team Leader審批,3-5天須要Manager審批,大於5天須要Director審批,這就造成了一個職責鏈。假如你要請假1個月,系統首先把請求傳遞給Leader對象,Leader對象發現本身沒法處理這個請求,將請求傳遞給Manager對象,Manager也沒法處理,再傳遞給Director。ide
定義一個處理請求的接口。this
實際負責處理請求的類。若是符合條件,處理該請求,不然轉發給後續的ConcreteHandler。spa
聲明抽象類Handler,定義一個處理請求的接口。code
public abstract class Handler { protected Handler _successor; public void SetSuccessor(Handler successor) { this._successor = successor; } public abstract void Handle(int request); }
具體實現類,負責處理請求。ConcreteHanlder1處理reqeust小於等於10的請求,其餘由ConcreteHandler2進行處理。對象
class ConcreteHandler1 : Handler { public override void Handle(int request) { if (request <= 10) { Console.WriteLine($"{this.GetType().Name} handled request {request}"); } else if (_successor != null) { _successor.Handle(request); } } } class ConcreteHandler2 : Handler { public override void Handle(int request) { if (request > 10) { Console.WriteLine($"{this.GetType().Name} handled request {request}"); } else if (_successor != null) { _successor.Handle(request); } } }
客戶端調用,設置職責鏈h1 -> h2,依次對requests數組中的元素進行處理。blog
class Program { static void Main(string[] args) { ConcreteHandler1 h1 = new ConcreteHandler1(); ConcreteHandler2 h2 = new ConcreteHandler2(); h1.SetSuccessor(h2); int[] requests = { 1, 4, 5, 11, 24 }; foreach (var request in requests) { h1.Handle(request); } Console.ReadLine(); } }
輸出結果:接口
當用戶提交一個請求,請求將沿着職責鏈依次傳遞知道有一個ConcreteHandler對象負責處理它。get
回到本篇開頭請假申請的示例,本節咱們將經過職責鏈模式來實現它,首先建立請求類LeaveReqeust,包含申請人以及申請天數,
class LeaveRequest { public string Applicant { get; set; } public int Days { get; set; } }
聲明抽象類Approver,定義一個處理請求的抽象方法Approve。
abstract class Approver { protected Approver _successor; public void SetSuccessor(Approver successor) { _successor = successor; } public abstract void Approve(LeaveRequest request); }
聲明Leader、Manager、Director三個實際處理請求的類。
class Leader : Approver { public override void Approve(LeaveRequest request) { if (request.Days <= 2) { Console.WriteLine($"{this.GetType().Name} approved request {request.Applicant},{request.Days}"); } else if (_successor != null) { _successor.Approve(request); } } } class Manager : Approver { public override void Approve(LeaveRequest request) { if (request.Days <= 5) { Console.WriteLine($"{this.GetType().Name} approved request {request.Applicant},{request.Days}"); } else if (_successor != null) { _successor.Approve(request); } } } class Director : Approver { public override void Approve(LeaveRequest request) { Console.WriteLine($"{this.GetType().Name} approved request {request.Applicant},{request.Days}"); } }
客戶端調用,建立職責鏈leader->manager->director,接着建立3個請求傳遞給職責鏈,依次處理。
class Program { static void Main(string[] args) { Leader leader = new Leader(); Manager manager = new Manager(); Director director = new Director(); leader.SetSuccessor(manager); manager.SetSuccessor(director); LeaveRequest jack = new LeaveRequest { Applicant = "Jack", Days = 2 }; LeaveRequest tom = new LeaveRequest { Applicant = "Tom", Days = 30 }; LeaveRequest mike = new LeaveRequest { Applicant = "Mike", Days = 4 }; leader.Approve(jack); leader.Approve(tom); leader.Approve(mike); Console.ReadLine(); } }
輸出結果:
由多個對象處理一個請求,在運行時肯定具體使哪一個對象進行處理
職責鏈能夠動態指定