zoukankan      html  css  js  c++  java
  • 代理设计模式

    什么是代理模式

    为其他对象提供一种代理以控制对这个对象的访问。

    为什么使用代理模式

    中介隔离:在某些情况下,一个客户类不想或者不能直接引用一个委托对象,而代理类对象可以在客户类和委托对象之间起到中介的作用,其特征是代理类和委托类实现相同的接口。

     

    开闭原则,增加功能代理类除了是客户类和委托类的中介之外,我们还可以通过给代理类增加额外的功能来扩展委托类的功能,这样做我们只需要修改代理类而不需要再修改委托类,符合代码设计的开闭原则。代理类主要负责为委托类预处理消息、过滤消息、把消息转发给委托类,以及事后对返回结果的处理等。代理类本身并不真正实现服务,而是同过调用委托类的相关方法,来提供特定的服务。真正的业务功能还是由委托类来实现,但是可以在业务功能执行的前后加入一些公共的服务。例如我们想给项目加入缓存、日志这些功能,我们就可以使用代理类来完成,而没必要打开已经封装好的委托类。

    代理模式实现原理

    代理模式主要包含三个角色,即抽象主题角色(Subject)、委托类角色(被代理角色,Proxied)以及代理类角色(Proxy),如下图所示:

     

    抽象主题角色:可以是接口,也可以是抽象类;

    委托类角色:真实主题角色,业务逻辑的具体执行者;

    代理类角色:内部含有对真实对象RealSubject的引用,负责对真实主题角色的调用,并在真实主题角色处理前后做预处理和后处理。

    代理模式应用场景

    SpringAop、日志收集、权限控制、过滤器、RPC远程调用

    代理模式创建的方式

    静态代理和动态代理

    静态代理

    静态代理是由程序员创建或工具生成代理类的源码,再编译代理类。

    所谓静态也就是在程序运行前就已经存在代理类的字节码文件,代理类和委托类的关系在运行前就确定了。

    一句话,自己手写代理类就是静态代理。

    动态代理

    动态代理是在实现阶段不用关心代理类,而在运行阶段才指定哪一个对象。

    动态代理类的源码是在程序运行期间由JVM根据反射等机制动态的生成 。

    JDK动态代理

    JDK动态代理的一般步骤如下:

    1.创建被代理的接口和类;

    2.实现InvocationHandler接口,对目标接口中声明的所有方法进行统一处理;

    3.调用Proxy的静态方法,创建代理类并生成相应的代理对象;

    CGLIB动态代理

    Cglib是一个强大的,高性能,高质量的代码生成类库。它可以在运行期扩展JAVA类与实现JAVA接口。其底层实现是通过ASM字节码处理框架来转换字节码并生成新的类。大部分功能实际上是ASM所提供的,Cglib只是封装了ASM,简化了ASM操作,实现了运行期生成新的class。

    CGLIB原理

    运行时动态的生成一个被代理类的子类(通过ASM字节码处理框架实现),子类重写了被代理类中所有非final的方法。在子类中采用方法拦截的技术拦截所有父类方法的调用,顺势植入横切逻辑。

    Cglib优缺点

    优点:JDK动态代理要求被代理的类必须实现接口,当需要代理的类没有实现接口时Cglib代理是一个很好的选择。另一个优点是Cglib动态代理比使用java反射的JDK动态代理要快

    缺点:对于被代理类中的final方法,无法进行代理,因为子类中无法重写final函数

    CGLIB代理实现

    实现MethodInterceptor接口的intercept方法后,所有生成的代理方法都调用这个方法。

    intercept方法的具体参数有

    obj 目标类的实例

    1. method 目标方法实例(通过反射获取的目标方法实例)

    2. args 目标方法的参数

    3. proxy 代理类的实例

    该方法的返回值就是目标方法的返回值。

    静态代理与动态代理区别

    静态代理需要自己写代理类,而动态代理不需要写代理类。

    JDK动态代理CGLIB实现区别

    JDK动态代理底层实现:

    JDK的动态代理使用Java的反射技术生成动态代理类,只能代理实现了接口的类, 没有实现接口的类不能实现动态代理。

    CGLIB动态代理底层实现:

    运行时动态的生成一个被代理类的子类(通过ASM字节码处理框架实现),子类重写了被代理类中所有非final的方法,在子类中采用方法拦截的技术拦截所有父类方法的调用,不需要被代理类对象实现接口,从而CGLIB动态代理效率比Jdk动态代理反射技术效率要高。

  • 相关阅读:
    python利用ffmpeg工具将视频帧推流至rtsp
    高斯曲线拟合
    Fast角点检测
    Harris角点检测和ShiTomasi角点检测
    python赋值,浅拷贝,深拷贝
    自适应阈值二值化
    Queue模块
    threading模块
    pycharm2020.3.3安装使用教程(2021.5.2更新)
    值得推荐的C/C++框架和库
  • 原文地址:https://www.cnblogs.com/ming-blogs/p/10878342.html
Copyright © 2011-2022 走看看