C# 设计模式-责任链模式

一.介绍  

  责任链模式(Chain of Responsibility Pattern)。属于行为型模式。它使多个对象都有机会处理请求,从而避免发送者和接受者之间的耦合关系。将这个对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。

二.实现

  举个例子,在一所银行里,有几个级别的员工,柜员、主管、经理。如果有人来存款,柜员只能处理10000元以内的取款业务,超出了就只能传递给他的上级主管去处理。主管只能处理100000元的业务,超出了就只能传递给他的上级经理去处理。在使用责任链模式前,试一下用普通的方式去实现。

public static void WithDrawMoney(decimal amount)
{
    // 柜员处理
    if (amount < 10000)
    {
        Console.WriteLine("柜员提取的金额");
    }
    // 主管处理
    else if (amount < 100000)
    {
        Console.WriteLine("主管提取的金额");
    }
    else
    {
        Console.WriteLine("经理提取的金额");
    }
}

  用这种 if / else 的方式,如果新增了一个级别的员工,处理起来会很麻烦,也违背开闭原则。而且,处理业务必须从最下级开始,限制高级员工的条件,如经理就处理不了10000元以内的业务。使用责任链模式可以解决这个问题。

//抽象处理者
public abstract class Handler
{
    protected Handler nextHandler;

    //设置下一级处理人
    public void SetHandler(Handler handler)
    {
        this.nextHandler = handler;
    }

    public abstract void HandleRequest(decimal amount);

}

//柜员
public class Teller : Handler
{
    public override void HandleRequest(decimal amount)
    {
        if (amount < 10000)
        {
            Console.WriteLine("柜员提取的金额:"+ amount);
        }
        else if (this.nextHandler != null)
        {
            Console.WriteLine("柜员无法处理,转主管");
            nextHandler.HandleRequest(amount);
        }
    }
}

//主管
public class Supervisor : Handler
{
    public override void HandleRequest(decimal amount)
    {
        if (amount < 100000)
        {
            Console.WriteLine("主管提取的金额:" + amount);
        }
        else if (this.nextHandler != null)
        {
            Console.WriteLine("主管无法处理,转经理");
            nextHandler.HandleRequest(amount);
        }
    }
}

//经理
public class BankManager : Handler
{
    public override void HandleRequest(decimal amount)
    {
        Console.WriteLine("银行经理提取的金额:" + amount);
    }
}

//调用
public static void Main(string[] args)
{
    Handler teller = new Teller();//柜员
    Handler supervisor = new Supervisor();//主管
    Handler bankManager = new BankManager();//经理

    teller.SetHandler(supervisor);//定义柜员上级为主管
    supervisor.SetHandler(bankManager);//定义主管上级为经理

    //
    Console.WriteLine("柜员处理不同金额的业务");
    Console.WriteLine("客户存9000");
    teller.HandleRequest(9000);
    Console.WriteLine();
    Console.WriteLine("客户存90000");
    teller.HandleRequest(90000);
    Console.WriteLine();
    Console.WriteLine("客户存150000");
    teller.HandleRequest(150000);
    Console.WriteLine();

    //
    Console.WriteLine("柜员请假,业务都由主管处理");
    Console.WriteLine("客户存9000");
    supervisor.HandleRequest(9000);
    Console.WriteLine();
    Console.WriteLine("客户存90000");
    supervisor.HandleRequest(90000);
    Console.WriteLine();
    Console.WriteLine("客户存150000");
    supervisor.HandleRequest(150000);
    Console.WriteLine();
}

三.总结

  优点:

  1.降低了请求的发送者和接受者之间的耦合。

  2.把多个条件判断分散到各个处理类中,使得代码更加清晰,责任更加明确。

  缺点:

  1.在找到正常的处理对象之前,所有的条件判断都要执行一遍,当责任链过长时,会引起性能问题。

  2.可能导致某个请求不被处理。

原文地址:https://www.cnblogs.com/shadoll/p/14343254.html