1.简介
1)模式概述:使多个对象都有机会处理请求,从而避免请求的发送者和接受者之间的耦合关系。将这个对象连成一条链,当客户提交请求时,请求沿着这条链传递,直到有一个对象处理它为止。
2)核心:利用多态性来化解分支带来的僵化。
2.UML与代码实现
1)结构:UML
模式组成:
抽象处理者角色(Handler):定义一个处理请求的接口,和一个后继连接(可选)
具体处理者角色(ConcreteHandler):处理它所负责的请求,可以访问它的后继者,如果可以处理请求则处理,否则将该请求转给他的后继者。
客户类(Client):向链上的具体处理者ConcreteHandler对象提交请求。
2)vb.net代码(用职责链计算上机消费时间)
抽象处理者:时间管理类TimeHandler
Public MustInherit Class CORTimeHandlerBLL Protected successor As CORTimeHandlerBLL ''' <summary> ''' 处理请求的抽象方法 ''' </summary> ''' <remarks></remarks> Public MustOverride Function HandTime(ByVal time As Integer) As Integer ''' <summary> ''' 设置继承者 ''' </summary> ''' <param name="successor"></param> Public Sub setsuccess(ByVal successor As CORTimeHandlerBLL) Me.successor = successor End Sub End Class
具体处理者1:准备时间PrepareTime
Public Class CORPrepareTimeBLL : Inherits CORTimeHandlerBLL Dim prepareTime As Integer Public Sub New(ByVal endataBase As List(Of DataBaseEntity)) Me.prepareTime = CInt(endataBase(0).ProPrepareTime) End Sub ''' <summary> ''' 准备时间 ''' </summary> ''' <param name="time">消费时间</param> Public Overrides Function HandTime(ByVal time As Integer) As Integer If time <= prepareTime Then Return 0 Else Return successor.HandTime(time) End If End Function End Class
具体处理者2:最少上机时间LeastTime
Public Class CORLeastTimeBLL : Inherits CORTimeHandlerBLL Private leastTime As Integer ''' <summary> ''' 构造函数,传入至少上机时间的值 ''' </summary> ''' <param name="endatabase"></param> ''' <remarks></remarks> Public Sub New(ByVal endatabase As List(Of DataBaseEntity)) Me.leastTime = CInt(endatabase(0).ProLeastTime) End Sub ''' <summary> ''' 准备时间 ''' </summary> ''' <param name="time">消费时间</param> Public Overrides Function HandTime(ByVal time As Integer) As Integer '如果上机时间小于至少上机时间,则返回时间 If time <= leastTime Then Return leastTime Else Return successor.HandTime(time) '否则转到下一位继承者 End If End Function End Class
具体处理者3:单位消费时间UnitTime
Public Class CORUnitTimeBLL : Inherits CORTimeHandlerBLL Private unitTime As Integer ''' <summary> ''' 构造函数,传入递增时间的值 ''' </summary> ''' <param name="endataBase"></param> ''' <remarks></remarks> Public Sub New(ByVal endataBase As List(Of DataBaseEntity)) Me.unitTime = CInt(endataBase(0).ProUnitTime) End Sub ''' <summary> ''' 大于至少上机时间,返回实际消费时间 ''' </summary> ''' <param name="time">消费时间</param> Public Overrides Function HandTime(ByVal time As Integer) As Integer Return Math.Abs(Int(-time / unitTime)) * unitTime End Function End Class
客户端:计算上机时间OnlineCount
''' <summary> ''' 调用职责链模式,计算出处理后时间 ''' </summary> Public Class OnLineCountBLL ''' <summary> ''' 职责链处理,计算消费时间 ''' </summary> ''' <param name="endataBase">基本数据设定类</param> ''' <param name="enLine">上机实体类</param> Public Function CostTime(ByVal endataBase As List(Of DataBaseEntity),ByVal enLine As LineEntity) As Integer '实例化类,通过构造函数,传递参数 Dim bprepareTime As New CORPrepareTimeBLL(endataBase) Dim bleastTime As New CORLeastTimeBLL(endataBase) Dim bunitTime As New CORUnitTimeBLL(endataBase) '设置职责链继承者 bprepareTime.setsuccess(bleastTime) bleastTime.setsuccess(bunitTime) '计算上下机时间差 Dim time As Integer time = DateDiff("n",enLine.ProOnDateTime,enLine.ProOffDateTime) Return bprepareTime.HandTime(time) '职责链处理,返回上机时间 End Function End Class
3.优点
1 ) 降低耦合度 :该模式使得一个对象无需知道是其他哪一个对象处理其请求。对象仅需知道该请求会被“正确”地处理。接收者和发送者都没有对方的明确的信息,且链中的对象不需知道链的结构。
2) 职责链可简化对象的相互连接,它们仅需保持一个指向其后继者的引用,而不需保持它所有的候选接受者的引用。
3) 增强了给对象指派职责的灵活性 ,当在对象中分派职责时,职责链可以提供更多的灵活性。可以通过在运行时刻对该链进行动态的增加或修改来增加或改变处理一个请求的那些职责,也可以将这种机制与静态的特例化处理对象的继承机制结合起来使用。
4)增加新的请求处理类很方便
4.应用
1)有多个的对象可以处理一个请求,哪个对象处理该请求运行时刻自动确定。
2)你想在不明确指定接收者的情况下,向多个对象中的一个提交一个请求。
3)可动态指定一组对象处理请求。
5.其它相关模式
职责链模式常与组合模式一起使用
小结
职责链模式的主要优点在于可以降低系统的耦合度,简化对象的相互连接,同时增强给对象指派职责的灵活性,增加新的请求处理类也很方便;其主要缺点在于不能保证请求一定被接收或处理,且对于比较长的职责链,请求的处理可能涉及到多个处理对象,系统性能将受到一定影响,而且在进行代码调试时不太方便。
原文链接:https://www.f2er.com/vb/257686.html