设计模式(C#)——责任链模式
Posted 小木工作室
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了设计模式(C#)——责任链模式相关的知识,希望对你有一定的参考价值。
大家好,这里是小木游戏,我是小木子。
今天我们继续学习设计模式中的责任链模式。Are you ready?
(每一个形状都是爱你的样子)
前言
在开发游戏过程中,当玩家合成一种道具的时候,对于不同的道具,需要的碎片个数,类型是不同的。用传统的写法,就是使用if…else…语句来判断。如果后面,策划修改了道具合成机制,我们就需要更改if结构判断了,这就违背了设计模式原则中的对扩展的开发,对修改的关闭,为此,我们引入责任链模式。
介绍
责任链模式(Chain of Responsibility Pattern)为请求创建了一个接收者对象的链。通常每个接收者都包含对另一个接收者的引用。如果一个对象不能处理该请求,那么它会把相同的请求传给下一个接收者,依此类推。
要素
1.抽象处理者(Handler):定义出一个处理请求的接口。如果需要,接口可以定义 出一个方法以设定和返回对下家的引用。
2.具体处理者(ConcreteHandler):具体处理者接到请求后,可以选择将请求处理掉,或者将请求传给下家。由于具体处理者持有对下家的引用,因此,如果需要,具体处理者可以访问下家。
3.请求类(Request):处理者需要处理的请求信息;
实现
这里我们还是用上面的例子,使用责任链模式来实现道具的合成机制。
1.创建请求类
//请求类,请求合成道具 public class SyntheticRequest { /// 当前拥有的碎片数量 public int DebrisNum{ get; set; } public SyntheticRequest(int num) { this.DebrisNum= num; } }
2.创建抽象角色类
//抽象角色类,可以通过合成得到的道具 public abstract class Prop { //下一级道具,更低一级的道具 public Prop NextProp{ get; set; } //当前道具类型 public string PropType{ get; set; } //构造函数 public Prop(string type) { this.PropType= type; } /// 该角色的执行行为 public abstract void Behaviour(SyntheticRequest request); }
3.创建具体角色类
///高级道具 public class Prop1:Prop { public Prop1(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 1000) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } } ///中级道具 public class Prop2:Prop { public Prop2(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 500) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } } ///低级道具 public class Prop3:Prop { public Prop3(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 10) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } }
4.使用责任链模式
//使用责任链模式 class Program { static void Main(string[] args) { //申请合成道具 SyntheticRequest request= new SyntheticRequest(66); //对该活动的审批可能涉及的角色 Prop prop1= new Prop1("高级道具"); Prop prop2= new Prop2("中级道具"); Prop prop3= new Prop3("低级道具"); //设置责任链 prop1.NextProp = prop2; prop2.NextProp = prop3; //合成处理 prop1.Behaviour(request); } }
整合代码
using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threading.Tasks; namespace 责任链模式{ //请求类,请求合成道具 public class SyntheticRequest { /// 当前拥有的碎片数量 public int DebrisNum{ get; set; } public SyntheticRequest(int num) { this.DebrisNum= num; } } //抽象角色类,可以通过合成得到的道具 public abstract class Prop { //下一级道具,更低一级的道具 public Prop NextProp{ get; set; } //当前道具类型 public string PropType{ get; set; } //构造函数 public Prop(string type) { this.PropType= type; } /// 该角色的执行行为 public abstract void Behaviour(SyntheticRequest request); } ///高级道具 public class Prop1:Prop { public Prop1(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 1000) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } } ///中级道具 public class Prop2:Prop { public Prop2(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 500) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } } ///低级道具 public class Prop3:Prop { public Prop3(string type) : base(type) { } public override void Behaviour(SyntheticRequest request) { if (request.DebrisNum>= 10) { Console.WriteLine("获得{0},消耗{1}碎片", this.PropType,request.DebrisNum); } else if (NextProp != null) { Console.WriteLine("{0}个碎片不够,只能合成更低一级的道具,即{1}", request.DebrisNum, NextProp.PropType); NextProp.Behaviour(request); } } } //使用责任链模式 class Program { static void Main(string[] args) { //申请合成道具 SyntheticRequest request= new SyntheticRequest(66); //对该活动的审批可能涉及的角色 Prop prop1= new Prop1("高级道具"); Prop prop2= new Prop2("中级道具"); Prop prop3= new Prop3("低级道具"); //设置责任链 prop1.NextProp = prop2; prop2.NextProp = prop3; //合成处理 prop1.Behaviour(request); } }}
优缺点
优点:
降低了请求的发送者和接收者之间的耦合;把多个条件判定分散到各个处理类中,使得代码更加清晰,责任更加明确。
缺点:
在找到正确的处理对象之前,所有的条件判定都要执行一遍,当责任链过长时,可能会引起性能的问题;可能导致某个请求不被处理。
总结
代码中存在多个if-else语句的情况下,此时可以考虑使用责任链模式来对代码进行重构。
注意
这里举的例子,在实际开发过程中可能不会用到设计模式,希望各位读者切勿固步自封。
(每一个形状都是爱你的样子)
-END-
喜欢本文的朋友们,欢迎关注订阅号,收看更多精彩内容!
以上是关于设计模式(C#)——责任链模式的主要内容,如果未能解决你的问题,请参考以下文章