行为型模式 - 责任链模式Chain of Responsibility

我就想知道我又哪里有广告植入了,告诉我。

学习而来,代码是自己敲的。也有些自己的理解在里边,有问题希望大家指出。

模式的定义与特点

       责任链(Chain of Responsibility)模式的定义:为了避免请求发送者与多个请求处理者耦合在一起,于是将所有请求的处理者通过前一对象记住其下一个对象的引用而连成一条链;当有请求发生时,可将请求沿着这条链传递,直到有对象处理它为止。  

       注意:责任链模式也叫职责链模式。  

      在责任链模式中,客户只需要将请求发送到责任链上即可,无须关心请求的处理细节和请求的传递过程,请求会自动进行传递。所以责任链将请求的发送者和请求的处理者解耦了。  

责任链模式其主要优点如下。

  • 降低了对象之间的耦合度。该模式使得一个对象无须知道到底是哪一个对象处理其请求以及链的结构,发送者和接收者也无须拥有对方的明确信息。
  • 增强了系统的可扩展性。可以根据需要增加新的请求处理类,满足开闭原则。
  • 增强了给对象指派职责的灵活性。当工作流程发生变化,可以动态地改变链内的成员或者调动它们的次序,也可动态地新增或者删除责任。
  • 责任链简化了对象之间的连接。每个对象只需保持一个指向其后继者的引用,不需保持其他所有处理者的引用,这避免了使用众多的 if 或者 if···else 语句。
  • 责任分担。每个类只需要处理自己该处理的工作,不该处理的传递给下一个对象完成,明确各类的责任范围,符合类的单一职责原则。

其主要缺点如下。

  • 不能保证每个请求一定被处理。由于一个请求没有明确的接收者,所以不能保证它一定会被处理,该请求可能一直传到链的末端都得不到处理。
  • 对比较长的职责链,请求的处理可能涉及多个处理对象,系统性能将受到一定影响。
  • 职责链建立的合理性要靠客户端来保证,增加了客户端的复杂性,可能会由于职责链的错误设置而导致系统出错,如可能会造成循环调用。

模式的结构与实现

通常情况下,可以通过数据链表来实现职责链模式的数据结构。  

1. 模式的结构

职责链模式主要包含以下角色。

  • 抽象处理者(Handler)角色:定义一个处理请求的接口,包含抽象处理方法和一个后继连接。
  • 具体处理者(Concrete Handler)角色:实现抽象处理者的处理方法,判断能否处理本次请求,如果可以处理请求则处理,否则将该请求转给它的后继者。
  • 客户类(Client)角色:创建处理链,并向链头的具体处理者对象提交请求,它不关心处理细节和请求的传递过程。

                

        责任链模式的本质是解耦请求与处理,让请求在处理链中能进行传递与被处理;理解责任链模式应当理解其模式,而不是其具体实现。责任链模式的独到之处是将其节点处理者组合成了链式结构,并允许节点自身决定是否进行请求处理或转发,相当于让请求流动起来。  

其结构图如图 1 所示。客户端可按图 2 所示设置责任链。  

图1 责任链模式的结构图

 ​​​​​

图 2

using DesignPattern.ChainofResponsibilityPattern;
using System;

namespace DesignPattern
{
    internal class Program
    {
        static void Main(string[] args)
        {
            ChainofResponsibilityHelper();
        }

        #region Pattern - ChainofResponsibility
        static void ChainofResponsibilityHelper()
        {
            int[] _arr_Numbers = new int[] { 27, 18, 14, 4, -7, 99, 0 };
            ChainofResponsibility item1 = new ChainofResponsibilityItem1();
            ChainofResponsibility item2 = new ChainofResponsibilityItem2();
            ChainofResponsibility item3 = new ChainofResponsibilityItem3();
            item1.SetNext(item2);
            item2.SetNext(item3);

            for (int i = _arr_Numbers.Length - 1; i >= 0; i--)
            {
                item1.DisposeHandler(_arr_Numbers[i]);
            }

            Console.ReadLine();
        }
        #endregion
    }
}
//==============================================================================================================


using System;

namespace DesignPattern.ChainofResponsibilityPattern
{
    public abstract class ChainofResponsibility
    {
        public abstract string Name { get; }
        public ChainofResponsibility NextChain { get; protected set; }

        public abstract void SetNext(ChainofResponsibility nextChain);
        public abstract void DisposeHandler(int number);
    }

    public class ChainofResponsibilityItem1 : ChainofResponsibility
    {
        public override string Name => "我在责任链位置:1, 我处理的数为:";



        public override void DisposeHandler(int number)
        {
            if (number <= 10)
            {
                Console.WriteLine(Name + number);
            }
            else if(null != NextChain)
            {
                NextChain.DisposeHandler(number);
            }
            else
            {
                Console.WriteLine(Name + number + ", 但这个数字无法处理");
            }
        }

        public override void SetNext(ChainofResponsibility nextChain)
        {
            NextChain = nextChain;
        }
    }
    public class ChainofResponsibilityItem2 : ChainofResponsibility
    {
        public override string Name => "我在责任链位置:2, 我处理的数为:";

        public override void DisposeHandler(int number)
        {
            if (number <= 20)
            {
                Console.WriteLine(Name + number);
            }
            else if (null != NextChain)
            {
                NextChain.DisposeHandler(number);
            }
            else
            {
                Console.WriteLine(Name + number + ", 但这个数字无法处理");
            }
        }

        public override void SetNext(ChainofResponsibility nextChain)
        {
            NextChain = nextChain;
        }
    }
    public class ChainofResponsibilityItem3 : ChainofResponsibility
    {
        public override string Name => "我在责任链位置:3, 我处理的数为:";

        public override void DisposeHandler(int number)
        {
            if (number <= 30)
            {
                Console.WriteLine(Name + number);
            }
            else if (null != NextChain)
            {
                NextChain.DisposeHandler(number);
            }
            else
            {
                Console.WriteLine(Name + number + ", 但这个数字无法处理");
            }
        }

        public override void SetNext(ChainofResponsibility nextChain)
        {
            NextChain = nextChain;
        }
    }
}

总结:

       责任链模式其实就是有很多个对象对其下家的引用而接起来形成一条链。请求在这个链上传递,直到链上的某一个对象决定处理此请求。客户并不知道链上的哪一个对象最终处理这个请求,系统可以在不影响客户端的情况下动态的重新组织链和分配责任。处理者有两个选择:承担责任或者把责任推给下家。一个请求可以最终不被任何接收端对象所接受。

      像是我们小时候写小纸条向后传一样,总有一个人会打开看并且停止传递行动,或者一直没人看,最后不了了之。


希望大家:点赞,留言,关注咯~    
😘😘😘😘

唠家常

        今日分享结束啦,小伙伴们你们get到了么,你们有没有更好的办法呢,可以评论区留言分享,也可以加QQ:841298494,大家一起进步。

  • 客官,看完get之后记得点赞哟!
  • 小伙伴你还想要别的知识?好的呀,分享给你们😄

今日推荐


http://www.niftyadmin.cn/n/1582001.html

相关文章

android原生定时任务_分布式调度任务系统调研及选型

目前的场景是这样的&#xff0c;我们组内现在有很多旧或新的定时任务都是在直接在某些服务器上跑。如果遇到要下线某台服务器&#xff0c;要先检查一下这个服务器上是否还存在定时任务脚本。通常情况下&#xff0c;即使找到该运行的定时任务脚本&#xff0c;也不知道它是用来做…

行为型模式 - 观察者模式Observer

学习而来&#xff0c;代码是自己敲的。也有些自己的理解在里边&#xff0c;有问题希望大家指出。 有一个大佬视频中提过一个案例&#xff0c;我觉得很棒&#xff1a;遥闻深巷中犬吠&#xff0c;边有妇人惊觉欠伸&#xff0c;其夫呓语。继而儿醒&#xff0c;大啼。夫亦醒。 模式…

idea redis图形化_对我来说数据库图形化管理工具用这个足够了

1. 前言我是一个有软件洁癖的人&#xff0c;能用现有的软件解决问题的绝不安装新的软件。Java后端开发主要跟数据库打交道&#xff0c;所以数据库图形化界面(GUI)是少不了的。通常图形化操作关系型数据库(RMDBS)大多数人会选择Navicat。如果你用的是Intellij IDEA&#xff0c;不…

als算法参数_CF的ALS算法推导

在上一篇中介绍了矩阵微分&#xff0c;现在就来牛刀小试一下。早些时候子龙问过我 Collaborative Filtering for Implicit Feedback Datasets这篇论文里的公式推导&#xff0c;在这里重新解一遍。论文里给出的目标函数为&#xff1a;$$\min_{x_*,y_*}\left\{\sum_{u,i}c_{ui}(p…

小米温控配置不见了_好戏来了!小米11屏幕下狠手,荣耀V40脱离华为正面刚小米...

小米11已经宣布28日发布&#xff0c;临近发布两天的时间开始疯狂预热。今天小米11预热的配置是所采用的屏幕&#xff0c;海报宣布可能是手机行业最贵的屏幕要打造高端屏幕新突破。雷军也在自己的微博上说&#xff0c;一块好的屏幕从清晰度到颜色&#xff0c;准确度从亮度到对比…

vue导入全局css_Github上一款受欢迎的基于Flexbox的现代纯CSS框架——bulma.css

介绍Bulma是一个免费的开源CSS框架&#xff0c;基于Flexbox(弹性布局)&#xff0c;已有200,000多名开发人员使用。Bulma和Bootstrap都是CSS框架&#xff0c;使开发人员可以轻松快速地构建Web界面。尽管它们具有相当相似的功能&#xff0c;但它们仍在某些方面有所不同。截止目前…

osm数据下载 python_python环境下实现ERA5逐小时数据的自动下载和简单处理

ERA5提供的下载代码#!/usr/bin/env python import cdsapic cdsapi.Client() c.retrieve(reanalysis-era5-land,{format: netcdf,variable: [2m_temperature, leaf_area_index_high_vegetation, leaf_area_index_low_vegetation,snow_cover, soil_temperature_level_1, surface…

asp登录页面的代码sqlserver_Serverless 解惑——函数计算如何访问 SQL Server 数据库...

函数计算&#xff08;Function Compute&#xff09;&#xff1a;函数计算 是事件驱动的全托管计算服务。使用函数计算&#xff0c;您无需采购与管理服务器等基础设施&#xff0c;只需编写并上传代码。函数计算为您准备好计算资源&#xff0c;弹性地可靠地运行任务&#xff0c;并…