设计模式19:Chain Of Responsibility 职责链模式(行为型模式)
Chain Of Responsibility 职责链模式(行为型模式)
请求的发送者与接受者
某些对象请求的接受者可能有多种多样,变化无常……

动机(Motivation)
在软件构建过程中,一个请求可能被多个对象处理,但是每个请求在运行时只能有一个接受者,如果显示指定,将必不可少地带来请求发送者与接受者的紧耦合。
如何使请求的发送者不需要指定具体的接受者?让请求的接受者自己在运行时决定来处理请求,从而使两者解耦。
意图(Intent)
使多个对象都有机会处理请求,从而避免请求的发送者和接受者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递请求,直到有一个对象处理它为止。——《设计模式》GoF
示例代码
public abstract class BaseHandler
{
public abstract void HandleRequest(Request request);
public abstract bool CanHandleRequest(Request request);
} public class AHandler : BaseHandler
{
public override void HandleRequest(Request request)
{
//...
} public override bool CanHandleRequest(Request request)
{
//...
}
} public class BHandler : BaseHandler
{
public override void HandleRequest(Request request)
{
//...
} public override bool CanHandleRequest(Request request)
{
//...
}
} public class CHandler : BaseHandler
{
public override void HandleRequest(Request request)
{
//...
} public override bool CanHandleRequest(Request request)
{
//...
}
} public class Request
{
//...
} public class Sender
{
public void Process()
{
Request request=new Request();
//...
List<BaseHandler> handlerList=new List<BaseHandler>();
handlerList.Add(new AHandler());
handlerList.Add(new BHandler());
handlerList.Add(new CHandler()); foreach (var handler in handlerList)
{
if (handler.CanHandleRequest(request))
{
handler.HandleRequest(request);
}
}
}
}
如果我们不希望Sender中有这么多的Handler的调用,可以通过指责链模式修改:
public abstract class BaseHandler
{
public BaseHandler(BaseHandler next)
{
this.Next = next;
} public BaseHandler Next { get; set; } protected abstract bool CanHandleRequest(Request request); public virtual void HandleRequest(Request request)
{
if (this.Next != null)
{
this.Next.HandleRequest(request);
}
}
} public class AHandler : BaseHandler
{
public AHandler(BaseHandler next)
: base(next)
{
} public override void HandleRequest(Request request)
{
if (this.CanHandleRequest(request))
{
//...
}
else
{
base.HandleRequest(request);
}
} protected override bool CanHandleRequest(Request request)
{
//...
}
} public class BHandler : BaseHandler
{
public BHandler(BaseHandler next)
: base(next)
{
} public override void HandleRequest(Request request)
{
//...
} protected override bool CanHandleRequest(Request request)
{
//...
}
} public class CHandler : BaseHandler
{
public CHandler(BaseHandler next)
: base(next)
{
} public override void HandleRequest(Request request)
{
//...
} protected override bool CanHandleRequest(Request request)
{
//...
}
} public class Request
{
//...
} public class Sender
{
public void Process(BaseHandler handler)
{
Request request = new Request();
//...
handler.HandleRequest(request);
}
}
客户端调用:
static void Main(string[] args)
{
Sender sender=new Sender(); BaseHandler handler1 = new AHandler(null);
BaseHandler handler2 = new BHandler(handler1);
BaseHandler handler3 = new CHandler(handler2); sender.Process(handler3); Console.ReadKey();
}
结构(Structure)

一个典型的对象结构可能如下图所示:

Handler——定义一个处理请求的接口。(可选)实现后继链。
ConcreteHandler——处理它所负责的请求。可访问它的后继者。如果可处理该请求,就处理之;否则将该请求转发给它的后继者。
Client——向链上的具体处理者(ConcreteHandler)对象提交请求。
Chain Of Responsibility 模式的几个要点
- Chain Of Responsibility 模式的应用场合在于“一个请求可能有多个接受者,但是最后真正的接受者只有一个”,只有这时候请求发送者与接受者的耦合才有可能出现“变化脆弱”的症状,职责链的目的就是将两者解耦,从而更好地应对变化。
- 应用了Chain Of Responsibility 模式后,对象的职责分派将更具灵活性。我们可以在运行时动态添加、修改请求的处理职责。
- 如果请求传递到职责链的末尾仍得不到处理,应该有一个处理的缺省机制。这也是每一个接受对象的责任,而不是发出请求的对象的责任。
- 这种链传递的方式效率较低。
转载请注明出处:
作者:JesseLZJ
出处:http://jesselzj.cnblogs.com
设计模式19:Chain Of Responsibility 职责链模式(行为型模式)的更多相关文章
- 设计模式(13)--Chain of Responsibility(责任链模式)--行为型
作者QQ:1095737364 QQ群:123300273 欢迎加入! 1.模式定义: 责任链模式是一种对象的行为模式.在责任链模式里,很多对象由每一个对象对其下家的引用而连接起来形成一 ...
- 设计模式学习笔记——Chain of Responsibility职责链模式
重点在链.一条链,如果本节点处理不了,则传递给下一个节点处理. 关键是如何传给下一个节点? 主要是由本节点决定传给哪一个节点. public class Client { public static ...
- python 设计模式之 (Chain of Responsibility)责任链模式
#写在前面 对于每一种设计模式,如果不理解它的原理和结构,是写不出例子来的.所以弄明白很重要. 等过完这段浑浑噩噩的日子,我要找个遍地开花的地方开怀大笑一场 #责任链模式定义 简书上一网友就把这个定义 ...
- go语言设计模式之Chain Of Responsibility(责任链)
ChainOfResponsibility.go package ChainOfResponsibility import ( "fmt" "io" " ...
- C#设计模式学习笔记:(20)职责链模式
本笔记摘抄自:https://www.cnblogs.com/PatrickLiu/p/8109100.html,记录一下学习过程以备后续查用. 一.引言 今天我们要讲行为型设计模式的第八个模式--职 ...
- 设计模式之第13章-职责链模式(Java实现)
设计模式之第13章-职责链模式(Java实现) “请假都那么麻烦,至于么.”“咋的了?”“这不快过年了么,所以我想早两天回去,准备一下,买买东西什么的,然后去给项目经理请假,但是他说快过年了,所以这个 ...
- 基于.net 职责链来实现 插件模式
插件式的例子 QQ电脑管家,有很多工具列表,点一下工具下载后就可以开始使用了 eclipse ,X Server 等等 插件式的好处 插件降低框架的复杂性,把扩展功能从框架中剥离出来 让第三方有机会来 ...
- .net 职责链来实现 插件模式
.net 职责链来实现 插件模式 插件式的例子 QQ电脑管家,有很多工具列表,点一下工具下载后就可以开始使用了 eclipse ,X Server 等等 插件式的好处 插件降低框架的复杂性,把扩展功能 ...
- FactoryMethod工厂方法模式(创建型模式)
1.工厂方法模式解决的问题 现在有一个抽象的游戏设施建造系统,负责构建一个现代风格和古典风格的房屋和道路. 前提:抽象变化较慢,实现变化较快(不稳定) 整个抽象的游戏设施建造系统相对变化较慢,本例中只 ...
随机推荐
- 重置mysql的root用户密码
/etc/rc.d/init.d/mysql status /etc/rc.d/init.d/mysql stop mysqld_safe --skip-grant-tables& mysql ...
- Django的路由层(URLconf)
URL配置(URLconf)就像Django所支撑网站的目录.它的本质是URL与要为该URL调用的视图函数之间的映射表:你就是以这种方式告诉Django,对于客户端发来的某个URL调用哪一段逻辑代码对 ...
- Windbg基本命令应用总结
.cordll -ve -u -l //reload core dlls ------加载下载系统文件符号的URL---------- .sympath SRV*C:\Symbols*http://m ...
- Android Studio里面配置Tesseract
网上大多是eclipse的项目,因为我用的是AS,所以说一下怎么配置. 身份证图片资料来自百度. 一.导入相关文件 其实我们不用自己编译,可以把别人项目编译好的jar包和so库直接拿来用.因为识别的效 ...
- 修改android Studio SDK 路径产生的问题(模拟器不能启动了)
原因:将 c:\user\admin\appdata\android\sdk 修改为 F:\AndroidProgram\Sdk 原来的虚拟机不能用了,要新建虚拟机才可以.
- [转] C# 获取程序运行目录
来自 莫等闲也,原文 // 获取程序的基目录. System.AppDomain.CurrentDomain.BaseDirectory // 获取模块的完整路径. System.Diagnosti ...
- Redis实战——简单介绍
出自:https://www.cnblogs.com/moonlightL/p/7364107.html Redis简单介绍 Redis是一个开源,高级的键值存储和一个适用的解决方案,用于构建高性能, ...
- 转 Jquery实际应用,判断radio,selelct,checkbox是否选中及选中的值
jquery取radio单选按钮的值 $("input[name='items']:checked").val(); 另:判断radio是否选中并取得选中的值 如下所示: ...
- js原型和原型链[转]
附上原文出处:http://hzjavaeyer.group.iteye.com/group/wiki/3086-JavaScript-core-concepts 一.概念: 原型对象:JavaScr ...
- MenuItem属性
[MenuItem属性] The MenuItem attribute allows you to add menu items to the main menu. The MenuItem attr ...