代理模式

Posted afei1759

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了代理模式相关的知识,希望对你有一定的参考价值。

Java有三种代理模式:静态代理、jdk动态代理、cglib代理
    • 静态代理
      目的是对目标类的功能进行扩展
      //接口
      public interface ISing)
         public void msg();
      
      //目标类
      public class Sing implements ISing
          public void msg()
          System.out.println("我在唱歌...");
         
      
      //代理类
      public class SingProxy  implements ISing
          private Sing sing;
          public SingProxy( Sing s)
          this.sing=s;
      
      public void msg()
          //此处为额外添加的功能...
          this.sing.msg();
          //此处为额外添加的功能...
             
      
      //主类
      public class Main
          public static void main(String[] args)
          //目标对象
          ISing sing=new Sing();
          //代理对象
          SingProxy singProxy=new SingProxy(sing);
          //本质是执行目标对象的方法
          singProxy.msg();
         
      
      • jdk动态代理
      静态代理的缺点是要提前写出代理类,jdk动态代理则可以在运行时动态生成代理类,java底层封装了实现细节,所以代码非常简单,格式写法固定:调用Proxy类的静态方法newProxyInstance(),该方法会返回一个代理类的对象,该方法为
      static Object newProxyInstance(ClassLoader loader, Class<?>[] interfaces,InvocationHandler h )
      接收的三个参数依次为
      • ClassLoader loader:指定目标对象使用的类加载器,写法固定
      • Class<?>[] interfaces:指定目标对象实现的接口,写法固定
      • InvocationHandler h:事件处理接口,需传入一个实现类,一般直接使用匿名内部类
      //代码写法固定
      public class Test
            public static void main(String[] args) 
                Sing target = new Sing();
                ISing singProxy  = (ISinger) Proxy.newProxyInstance(
                        target.getClass().getClassLoader(),
                        target.getClass().getInterfaces(),
                        new InvocationHandler() 
                            @Override
                            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable 
                               System.out.println("此处为额外实现的功能...");
                               //执行目标对象方法
                               Object returnValue = method.invoke(target, args);
                               System.out.println("此处为额外实现的功能...");
                               return returnValue;
                           
                       );
              //调用后的本质是执行目标的msg方法
               singProxy.msg();
               
       静态代理和JDK代理类都必须实现一个或多个接口,若没有,则可以使用cglib代理。
      • cglib代理
        cglib代理也叫作子类代理,它构建一个目标类的子类(作为代理类),进而添加额外的功能,在Spring的AOP中,如果加入容器的目标类有实现接口,用JDK代理,若没有实现接口,用cglib代理。cglib代理对目标类的要求:
      Spring的核心包中已经包括了cglib功能,需直接引入spring-core-3.2.5.jar;
      目标类不能为final修饰;
      目标类的对象方法如果为final/static,那么就不会被拦截,即不会执行额外的功能,此时cglib失效;
      //目标类(没有接口)
      public class Sing
          public void msg()
          System.out.println("我在唱歌...");
         
      
      
      //Cglib工厂类
        public class ProxyFactory implements MethodInterceptor
            // 维护目标对象
            private Object target;
            public ProxyFactory(Object target) 
                this.target = target;
           
           // 给目标对象创建一个子类对象(子类代理对象,子类做代理类)
           public Object getProxyInstance()
               //1.工具类
               Enhancer en = new Enhancer();
               //2.设置父类
               en.setSuperclass(target.getClass());
               //3.设置回调函数
               en.setCallback(this);
               //4.创建目标类的子类对象(子类代理对象)
               return en.create();
          
      //代码写法固定
           @Override
           public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable 
               System.out.println("此处为额外实现的功能...");
               //执行目标对象的方法
               Object returnValue = method.invoke(target, args);
               System.out.println("此处为额外实现的功能...");
               return returnValue;
           
       
      
      //主类
      public class Main
                 public static void main(String[] args)
                //目标对象,没有接口
                Sing target = new Sing();
                //代理对象
                Sing proxy = (Sing)new ProxyFactory(target).getProxyInstance();
                proxy.msg();//执行子类代理对象的方法
           
       
       
       

以上是关于代理模式的主要内容,如果未能解决你的问题,请参考以下文章

设计模式代理模式 ( 代理模式结构 | 客户端 | 主题对象 | 被代理对象 | 代理对象 )

代理的模式和原理(代理的模式有几种)

设计模式——代理模式

设计模式-代理模式

设计模式 结构型模式 -- 代理模式(动态代理(CGLIB动态代理)三种代理的对比(静态代理动态代理(JDK代理和CGLIB代理)优缺点使用场景))

代理模式 (ProxyPattern)