责任链模式:使得多个对象都有机会处理请求,从而避免请求的发送者和接收者之间耦合关系。将这个对象串成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止
案例:
实现思路:先新建一个任务处理的一个接口类Handler,里面有一个执行的方法(execute),方法参数Bigdemic类型的参数(money)和一个委托者对象(HandlerChain),
三个实现类实现Handler接口,每个实现类有一个的审批金额的权限,AHandler审批的不能超过2000的,如果金额超过2000,交给BHandler来处理,如果BHandler处理不了,再
传递给下一个来处理,直到有一个来处理它为止。
代码实现:
1.Handler接口类
package edu.nf.demo2; import java.math.BigDecimal; /** * @author lance * @date 2018/10/17 * 任务处理接口 */ public interface Handler { /** * 抽象的任务处理方法 * @param money 审批金额 * @param chain 依赖一个链式处理器(委托者) */ void execute(BigDecimal money,HandlerChain chain); }
2. 三个实现类
2.1 AHandler
package edu.nf.demo2; import java.math.BigDecimal; /** * @author lance * @date 2018/10/17 */ public class AHandler implements Handler{ @Override public void execute(BigDecimal money, HandlerChain chain) { if(money.doubleValue() <= 2000){ System.out.println("AHandler 处理审批"); }else{ //递归交给chain去查找下一个处理者 chain.execute(money); } } }
2.2 BHandler
package edu.nf.demo2; import java.math.BigDecimal; /** * @author lance * @date 2018/10/17 */ public class BHandler implements Handler{ @Override public void execute(BigDecimal money, HandlerChain chain) { if(money.doubleValue() <= 5000){ System.out.println("BHndler 处理审批"); }else{ //递归交给chain去查找下一个处理者 chain.execute(money); } } }
2.3 CHandler
package edu.nf.demo2; import java.math.BigDecimal; /** * @author lance * @date 2018/10/17 */ public class CHandler implements Handler{ @Override public void execute(BigDecimal money, HandlerChain chain) { if(money.doubleValue() <= 10000){ System.out.println("CHandler 处理审批"); }else{ //递归交给chain去查找下一个处理者 chain.execute(money); } } }
3.这里通过一个委托者的类来进行链式处理,可以很好解决代码之间的耦合关系(注意:还需要一个配置文件,通过配置文件动态的找到所有的实现类)
package edu.nf.demo2; import java.math.BigDecimal; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import java.util.ServiceLoader; /** * @author lance * @date 2018/10/17 */ public class HandlerChain { /** * 声明一个迭代器 */ private Iterator<Handler> it; /** * 初始化所有的处理对象 */ public HandlerChain(){ //使用ServiceLoader类在加载所有的实现类对象(服务类) //并返回一个迭代器,迭代器中存放的就是配置文件的所有实现类对象 it = ServiceLoader.load(Handler.class).iterator(); } /** * 递归的链式处理 * @param money */ public void execute(BigDecimal money){ if(it.hasNext()){ it.next().execute(money, this); } } }
配置文件:如果是普通的项目,就在src要目录下新建一个 META-INF.services 的文件夹,不能打错,在这个文件夹下新建一个文件,文件名必须是完整包名加类名,
如果是Maven项目就建在resoures目录下
4.测试类:Main
package edu.nf.demo2; import java.math.BigDecimal; /** * @author lance * @date 2018/10/17 */ public class Main { public static void main(String[] args) { //创建一个链式处理器(委托者) HandlerChain chain = new HandlerChain(); //提交请求 chain.execute(new BigDecimal("6000")); } }
5.效果图