链式设计-------责任链模式和装饰模式
链式设计-------责任链模式和装饰模式
装饰模式:是为已有功能动态地添加更多功能的一种方式
角色:
原始对象:用原始功能,需要扩展其他的功能呢
公共接口:将中间类和功能拓展类以及原始对象的进行联系
中间类:寻找父亲,找到原始类,动态的添加职能
功能更拓展类:功能扩展
//公共类 Component
public interface ICharacter {
public void show();
}
//原始类
public class Person implements ICharacter{
private String name;
public Person(String name){
this.name = name;
}
public void show(){
System.out.println("装扮的"+name);
}
}
//中间类
public class Finery implements ICharacter{
protected ICharacter component;
public void decorate(ICharacter component)
{
this.component = component;
}
public void show()
{
if(component != null)
{
component.show();
}
}
}
//职能类
public class Dtx extends Finery {
public void show(){
System.out.print("大T恤");
super.show();
}
}
public class Pqx extends Finery {
public void show()
{
System.out.print("皮球鞋");
super.show();
}
}
public class Ydk extends Finery {
public void show()
{
System.out.print("运动裤");
super.show();
}
}
//客户端
public class Client {
public static void main(String[] args) {
Person xc = new Person("小菜");
// 创建 Person 对象:创建一个名为 "小菜" 的 Person 对象 xc。
Dtx dtx = new Dtx();
//建并装饰 Dtx 对象:创建一个 Dtx 对象 dtx,并将其装饰到 xc 上。
dtx.decorate(xc);
// 创创建并装饰 Ydk 对象:创建一个 Ydk 对象 ydk,并将其装饰到 dtx 上。
Ydk ydk = new Ydk();
ydk.decorate(dtx);
//创建并装饰 Pqx 对象:创建一个 Pqx 对象 pqx,并将其装饰到 ydk 上。
Pqx pqx = new Pqx();
pqx.decorate(ydk);
//调用 show 方法:调用 pqx 的 show 方法,展示最终的装饰结果。
pqx.show();
}
}
控制台:皮球鞋运动裤大T恤装扮的小菜
装饰模式基于开闭原则,即对扩展开放、对修改关闭。它允许通过组合而非继承的方式,灵活地为对象附加新特性,规避了因多层继承带来的复杂性与僵化问题。例如,开发一款咖啡售卖系统,基础款咖啡是原味咖啡,后续要增添摩卡、拿铁、焦糖等风味,使用装饰模式,就不用频繁修改原味咖啡类,只需新增风味装饰类即可。
优势
- 灵活性高:能够动态地组合不同装饰,按需为对象添加功能。开发图形绘制软件时,可随时给图形对象添加阴影、边框、渐变填充等装饰效果,不受限于固定功能组合。
- 扩展性强:新增装饰功能简单,只需新建具体装饰类,遵循抽象装饰类规范,融入现有体系轻松,利于系统迭代升级。
- 符合开闭原则:避免大面积修改原始代码,减少引入新 bug 的风险,降低维护成本,提升代码稳定性。
缺点
- 代码复杂性增加:装饰类层层嵌套,对象关系变得复杂,尤其当装饰链较长时,理解和调试的难度直线上升。在大型项目里,繁多的装饰类交织,追踪执行流程与定位错误成为棘手问题。
- 可读性降低:大量装饰类与组合操作,让代码结构不够直观,新加入开发团队的成员需花费较多时间理清装饰逻辑与功能流程。
责任链模式
责任链模式:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这个对象连成一条链,并沿着这个条链传递该请求,直到有一个对象处理为止。
角色:
公共类
中间类
-
优势
- 解耦请求发送者和接收者:请求发送者不需要知道具体哪个接收者会处理请求,只需要将请求发送到责任链的头部即可。这样可以降低系统的耦合度,使得系统的各个部分更加独立。例如,在一个电商系统的订单处理中,订单发送模块不需要知道具体是哪个环节处理了订单的具体部分,只需要将订单请求发送到责任链的头部。
- 动态组合处理者:可以方便地增加、删除或重新排列处理者。在软件的维护和升级过程中,如果需要添加一个新的处理者,比如在文件上传系统中添加一个文件权限检查器,只需要实现抽象处理者接口,然后将其插入到责任链中的合适位置即可。
- 灵活性和可扩展性:不同的处理者可以有不同的处理逻辑,每个处理者专注于自己的职责范围,使得系统的功能划分更加清晰。例如,在一个客户服务系统中,不同的客服人员可以根据自己的技能和权限处理不同类型的客户问题,这样的设计使得每个环节的功能相对独立,易于扩展和修改。
-
缺点
- 调试可能会比较复杂:由于请求在多个处理者之间传递,当出现问题时,很难确定是哪一个处理者导致的问题。特别是当处理者链比较长,而且每个处理者的处理逻辑比较复杂时,追踪问题的根源会变得更加困难。
- 可能会导致性能问题:如果处理者链很长,每个请求都需要经过多个处理者的检查,即使有些处理者最终不会处理这个请求,也会消耗一定的时间和资源。例如,在一个网络请求处理链中,如果有很多不必要的中间检查环节,可能会增加请求的响应时间。
abstract class Handler { protected Handler successor; public void setSuccessor(Handler successor){ this.successor = successor; }; public abstract void handleRequest(int request); } public class ConcreteHandler1 extends Handler{ public void handleRequest(int request){ if(request>=0&&request<=10){ System.out.println("ConcreteHandler1 handle request "+request); }else{ if(successor!=null){ successor.handleRequest(request); } } } } public class ConcreteHandler2 extends Handler{ public void handleRequest(int request) { if(request >= 10 && request < 20) { System.out.println("ConcreteHandler2 处理请求:" + request); } else if(successor != null) { successor.handleRequest(request); } } } public class ConcreteHandler3 extends Handler{ public void handleRequest(int request) { if(request>=20&&request<30) { System.out.println("---由第三个处理者处理---"); } else { if(successor!=null) { successor.handleRequest(request); } } } } public class Start { public static void main(String[] args) { // 创建一个请求 int request = 5; // 创建三个处理者 Handler handler1 = new ConcreteHandler1(); Handler handler2 = new ConcreteHandler2(); Handler handler3 = new ConcreteHandler3(); // 设置处理者链 handler1.setSuccessor(handler2); handler2.setSuccessor(handler3); // 处理请求 int [] result ={2,5,14,22,18,3,27,20}; for (int i=0;i<result.length;i++){ handler1.handleRequest(result[i]); } } }
-
应用场景
- 工作流审批系统:如请假申请、费用报销等审批流程,不同级别的审批者组成责任链,根据申请的金额、类型等因素依次审批。
- 事件处理系统:在图形用户界面(GUI)中,鼠标点击、键盘输入等事件可以通过责任链来处理。不同的组件(如窗口、按钮、文本框等)可以作为处理者,按照一定的层次结构来处理事件。
}
}
-
应用场景
- 工作流审批系统:如请假申请、费用报销等审批流程,不同级别的审批者组成责任链,根据申请的金额、类型等因素依次审批。
- 事件处理系统:在图形用户界面(GUI)中,鼠标点击、键盘输入等事件可以通过责任链来处理。不同的组件(如窗口、按钮、文本框等)可以作为处理者,按照一定的层次结构来处理事件。
- 日志记录系统:不同级别的日志(如 DEBUG、INFO、WARN、ERROR)可以由不同的日志处理者组成责任链来处理,根据日志级别将日志信息输出到不同的地方(如控制台、文件等)
原文地址:https://blog.csdn.net/weixin_60564529/article/details/144300381
免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!