【设计模式】责任是责任,链是链,责任链模式是什么?

这是我参与8月更文挑战的第3天,活动详情查看:8月更文挑战java

1、什么是责任链模式
1.先看看百度百科是怎么解释的

责任链模式是一种设计模式。在责任链模式里,不少对象由每个对象对其下家的引用而链接起来造成一条链。请求在这个链上传递,直到链上的某一个对象决定处理此请求。发出这个请求的客户端并不知道链上的哪个对象最终处理这个请求,这使得系统能够在不影响客户端的状况下动态地从新组织和分配责任。 ——百度百科spring

咱们能够理解到,责任链就是多个对象一块儿共同对一个请求进行处理,这里还提到的,直到链上的某一个对象决定处理此请求。若是只是有一个对象对请求进行处理的话,那为何要花费这么大的力气去组成这一条责任链呢?这不是画蛇添足吗?设计模式

2.我对责任链的见解

首先,责任链的这个设计模式,确定是将一个请求分散给多个对象处理,为了更加的直观方便,因而将处理对象串成一条链条,让它们一直调用下家来进行处理这个请求。 其次,责任链并非只有一个对象决定对请求进行处理,而是所有对象共同对这个请求进行处理,只是分别在不一样的维度上而已。tomcat

简单地画个图做为对责任链的描述 在这里插入图片描述markdown

3.使用责任链的优缺点
优势
  1. 让每一个类更加地专一本身的责任。
  2. 使编码过程更加的清晰。
  3. 下降耦合度。下降了代码的复杂度
  4. 新增或修改更加方便
缺点
  1. 处理存在延迟
  2. 不能保证请求必定被处理
  3. 责任链较长会影响系统性能
  4. 进行代码调试时不方便
原则

“+”表明遵照,“-”表明不遵照或者不相关ide

原则 开放封闭 单一职责 迪米特 里氏替换 依赖倒置 接口隔离 合成复用
+ + - - + - -
2、加强型责任链(过滤器)

由于感受跟加强型代理特别像,就比较大胆地将名字取成了加强型责任链,它也能够叫过滤器。工具

1.特色
  1. 最终处理对象不变
  2. 使用习惯不变
  3. 业务无关性
  4. 附加新功能
  5. 请求必定会被处理

总的来讲,加强型责任链的处理对象仍然是只有一个,很符合百度百科的解释,就是整一条责任链中,只有最后一个对象才会对请求进行处理,其余的都是在做一些记录,或者是上锁,都是一切无关业务的操做。加强型责任链更加侧重的点是无关业务逻辑的操做。post

2.常见的例子
  1. tomcat中的Filter接口,在请求的时候采用了这种加强型责任链,最终处理请求的对象没有改变,它是一层一层地将request和response传递给servlet对象处理的。
  2. struts2中也存在过滤器,具体用来干吗的,我也想不起来了,好像是用来校验的。
3、拦截器责任链
1.特色
  1. 最终处理对象不变
  2. 使用习惯不变
  3. 改变业务逻辑
  4. 请求不必定被处理

总的来讲,拦截器责任链会影响到业务的逻辑,一旦其中的一个对象验证时不符合条件,就会中断整个请求,就像是一系列的if包裹在一块儿。拦截器责任链更加侧重的点是业务逻辑。性能

2.常见的例子
  1. HandlerInterceptorAdapter类
  2. 一样是struts2里面也有拦截器,能够用做拦截用户无登录进入网站。
  3. spring中也有拦截器
4、过程型责任链(pipeline责任链)
1.特色
  1. 处理对象不单一
  2. 责任链对象顺序有要求
  3. 使用更加方便
  4. 业务无关性
  5. 请求必定会被处理

总的来讲,过程型责任链就是将一个请求分给多个对象进行处理,处理的顺序有些会存在严格要求,当所有对象都进行了处理以后就会返回。有点像连接型代理,对多个方法进行了封装,可是过程型责任链对处理的顺序有要求。过程型责任链更加侧重的点是处理的过程。测试

2.常见的例子
  1. Jenkins打包工具,它就是将源代码处理成字节码,再打包成wai包,而后发布。
5、总结

加强型责任链更加侧重的点是无关业务逻辑的操做。 拦截器责任链更加侧重的点是业务逻辑。 过程型责任链更加侧重的点是处理的过程。 这三个责任链分别从三个维度出发,造成了各有特点的责任链。 不排除之后会出现更多的责任链,可是它们的本质都是从不一样维度对一个请求进行处理,它们的形式都是一个链条。

6、责任链简单的实现方式

这是仿照tomcat里的过滤器责任链来实现的,想要实现其余的责任链,作出一些修改便可。

  1. 先建立一个Filter接口,做为责任链中存放对象的原型
package responsibilitychain;
​
/**
 * @author xxj
 * 过滤器
 */
public interface Filter {
    /**
     * 责任链中最终执行的方法
     * @param object 传递的须要处理的对象
     * @return 改为boolean的话就是拦截器了,
     */
    void doFilter(Object object);
}
复制代码
  1. 建立一个FilterChain类,做为责任链管理器
package responsibilitychain;
​
import java.util.ArrayList;
import java.util.List;
​
/**
 * @author xxj
 * 责任链管理器
 */
public class FilterChain implements Filter {
    List<Filter> list =new ArrayList<>();
    public void addFilter(Filter filter){
        list.add(filter);
    }
    @Override
    public void doFilter(Object object) {
        list.forEach(f -> f.doFilter(object));
    }
}
​
复制代码
  1. 使用责任链 每一个责任链对象都须要单首创建一个类,这个类须要实现Filter接口
package responsibilitychain;
​
/**
 * @author xxj
 * 测试责任链
 * 对一个String对象进行修改
 */
public class test {
    public static void main(String[] args){
        //建立责任链管理器
        FilterChain filterChain=new FilterChain();
        //添加责任链
        filterChain.addFilter(new FirstFilter());
        filterChain.addFilter(new SecondFilter());
        filterChain.addFilter(new LastFilter());
        //调用责任链
        String string="   aaa    ";
        filterChain.doFilter(string);
    }
    static class FirstFilter implements Filter{
        @Override
        public void doFilter(Object object) {
            //强转成String
            String string=(String)object;
            //输出String的长度
            System.out.println(string.length());
​
        }
    }
    static class SecondFilter implements Filter{
        @Override
        public void doFilter(Object object) {
            //强转成String
            String string=(String)object;
            //去掉空格
            string=string.trim();
            //再输出长度
            System.out.println(string.length());
        }
    }
    static class LastFilter implements Filter{
        @Override
        public void doFilter(Object object) {
            //强转成String
            String string=(String)object;
            //输出string
            System.out.println(string);
​
        }
    }
}
复制代码
  1. 输出的结果
10
3
   aaa    
​
复制代码

责任链模式除了这种实现方式以外,还有一种实现方式,定义跟过滤器同样的接口,名称的话叫chain也行,而后定义一些行为,这里的行为是须要跟你最终想要使用的对象同样,例如一个数据对象LogData有get和set方法,那这个接口就要有get和set方法,而后实现一系列的chain类,这些chain类内部须要声明一个chain的成员变量,这个成员用于指向下一个chain对象,还有get或set方法都须要去调用这个chain对象的get或set方法,接下来就是要组成咱们的责任链了,把一个个chain实现类的对象组成一条链子,在建立对象时就要传递下一个责任链节点的对象进入,直到最终想要使用的对象。

——————————————————————————————

你知道的越多,不知道的就越多。

若是本文章内容有问题,请直接评论或者私信我。若是以为我写得还不错的话,点个赞也是对个人支持哦

未经容许,不得转载!

相关文章
相关标签/搜索
本站公众号
   欢迎关注本站公众号,获取更多信息