zoukankan      html  css  js  c++  java
  • JDK与CGlib动态代理的实现

    应用的原型为

    执行者:房屋中介Agency(分为JDKAgency、CGlibAgency)

    被代理对象:程序员Programmer

    被代理对象的实现接口:租户Tenement(CGlibAgency时不需要实现接口)

    Tenement 接口:
    package com.suzao.spring.test;
    
    /**
     * Tenement
     * @Description 租户
     * @Param
     * @return
     * @Author mc
     * @Date 2018/12/28 16:44
     */
    public interface Tenement {
    
        /**
         * rentHouse
         * @Description 租房方法
         * @Param []
         * @return
         * @Author mc
         * @Date 2018/12/28 18:51
         */
        void rentHouse();
    }
    Programmer 实现类
    package com.suzao.spring.test;
    
    /**
     * Programmer
     * @Description 程序员
     * @Param
     * @return
     * @Author mc
     * @Date 2018/12/28 18:21
     */
    public class Programmer implements Tenement {
    
        /**
         * rentHouse
         * @Description 租房方法
         * @Param []
         * @return
         * @Author mc
         * @Date 2018/12/28 18:52
         */
        @Override
        public void rentHouse() {
            System.out.println("我是程序员,我在找房子!");
        }
    }

    JDK动态代理:执行者  JDKAgency 

    package com.suzao.spring.test;
    
    import java.lang.reflect.InvocationHandler;
    import java.lang.reflect.Method;
    import java.lang.reflect.Proxy;
    
    /**
     * JDKAgency
     * @Description JDK房屋中介
     * @Param
     * @return
     * @Author mc
     * @Date 2018/12/28 18:22
     */
    public class JDKAgency implements InvocationHandler{
    
        //拿到被代理对象的引用
        private Tenement target;
    
        public Object getTenementProxy(Tenement target){
            this.target = target;
            Class clazz = target.getClass();
            //clazz.getInterfaces() 获取它的接口
            //重新动态生成一个class字节码
            //编译
            return Proxy.newProxyInstance(clazz.getClassLoader(),clazz.getInterfaces(),this);
        }
    
        @Override
        public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
            System.out.println("JDK房屋中介开始执行。。。");
            System.out.println("----------------------------");
            method.invoke(this.target,args);
            System.out.println("----------------------------");
            System.out.println("JDK房屋中介结束执行。。。");
            return null;
        }
    }

    CGlib动态代理:执行者  CGlibAgency 

    package com.suzao.spring.test;
    
    import org.springframework.cglib.proxy.Enhancer;
    import org.springframework.cglib.proxy.MethodInterceptor;
    import org.springframework.cglib.proxy.MethodProxy;
    
    import java.lang.reflect.Method;
    
    /**
     * CGlibAgency
     * @Description CGlib 租房中介
     * @Param
     * @return
     * @Author mc
     * @Date 2018/12/28 19:11
     */
    public class CGlibAgency implements MethodInterceptor{
    
    
        public Object getTenmentProxy(Class clazz){
    
            Enhancer enhancer = new Enhancer();
    
            //告诉cglib,生成的子类需要继承那个类
            enhancer.setSuperclass(clazz);
    
            //设置回调
            enhancer.setCallback(this);
    
            //加载到jvm中,并返回代理对象
            return enhancer.create();
        }
    
        @Override
        public Object intercept(Object obj, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
            System.out.println("CGlib房屋中介开始执行。。。");
            System.out.println("----------------------------");
            methodProxy.invokeSuper(obj,args);
            System.out.println("----------------------------");
            System.out.println("CGlib房屋中介结束执行。。。");
            return null;
        }
    }

    代理测试类 TestProxy 

    package com.suzao.spring.test;
    
    /**
     * TestProxy
     * @Description 测试代理
     * @Param
     * @return
     * @Author mc
     * @Date 2018/12/28 18:46
     */
    public class TestProxy {
    
    
        public static void main(String[] args) {
    
            //java动态代理是利用反射机制生成一个实现被代理对象的接口的匿名类,在调用具体方法前调用InvokeHandler来处理。
    
            //执行者 JDKAgency
            //被代理对象 Programmer
            //被代理对象实现的接口 Tenement
            Tenement  tenement= (Tenement) new JDKAgency().getTenementProxy(new Programmer());
            tenement.rentHouse();
            System.out.println("
    
    ");
            
            //cglib动态代理利用asm开源包,对被代理对象类的class文件加载进来,通过修改其字节码生成子类来处理。
            //执行者 CGlibAgency
            //被代理对象 Programmer
            Programmer  programmer= (Programmer) new CGlibAgency().getTenmentProxy(new Programmer().getClass());
            programmer.rentHouse();
        }
    }

    执行结果:

    JDK房屋中介开始执行。。。
    ----------------------------
    我是程序员,我在找房子!
    ----------------------------
    JDK房屋中介结束执行。。。
    
    
    
    CGlib房屋中介开始执行。。。
    ----------------------------
    我是程序员,我在找房子!
    ----------------------------
    CGlib房屋中介结束执行。。。

    pom.xml中引用:

    <dependency>
                        <groupId>org.springframework</groupId>
                        <artifactId>spring-core</artifactId>
                        <version>${org.springframework-version}</version>
                    </dependency>
             <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-beans</artifactId>
                <version>${org.springframework-version}</version>
            </dependency>
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-aop</artifactId>
                <version>${org.springframework-version}</version>
            </dependency>
             <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-context</artifactId>
                <version>${org.springframework-version}</version>
            </dependency>
  • 相关阅读:
    10月20日动手动脑
    10月20日
    10月19日
    10月18日
    10月17日
    10月16日
    10月15日
    10月14日
    jQuery选择器大全
    面试总结
  • 原文地址:https://www.cnblogs.com/benefitworld/p/10192438.html
Copyright © 2011-2022 走看看