The case of jdk dynamic proxy and cglib dynamic proxy

acting

jdk dynamic proxy
/**
 * jdk动态代理
 * @author Administrator
 *
 */

public class JDKProxyDemo {

    private Object target;//目标类

    public JDKProxyDemo(Object target){
        this.target=target;
    }
    /**
     * 创建代理类方法
     * @param target
     * @return
     */
    public Object createProxyObject(){

        ClassLoader loader=target.getClass().getClassLoader();//目标类类加载器
        Class<?>[] interfaces=target.getClass().getInterfaces();//目标类所实现的所有接口
        InvocationHandler h=new InvocationHandler() {   
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                System.out.println("jdkProxyDemo");
                Object obj = method.invoke(target, args);//对原始操作进行调用(反射)
                return obj;
            }
        };
        Object object = Proxy.newProxyInstance(loader, interfaces, h);
        return object;

    }   
}
cglib dynamic proxy

/**
 * cglib代理案例
 * @author Administrator
 *
 */
public class CglibProxyDemo {

    private Object target;//目标类

    public CglibProxyDemo(Object target){
        this.target=target;
    }

    public Object createProxyObject(){

        //1.创建内存中的动态类   Enhancer
        //内存中造出一个没有名称的动态类
        Enhancer enhancer=new Enhancer();
        //2.现在的类最终完成目标类的功能,同时对其进行功能的增强,必须先具有目标类对应的功能————继承
        enhancer.setSuperclass(target.getClass());
        ////3.进行功能的增强
        //设置了方法的调用拦截
        //设置具体的回调操作
        Callback callback = new MethodInterceptor() {
            //proxy:代理对象
            //method:被拦截的方法对象
            //args:调用参数
            //methodProxy:
            @Override
            public Object intercept(Object proxy, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
                System.out.println("cglib");

                //Object obj=method.invoke(proxy, args);//这种执行是代理类的方法,而不是目标类的,会造成内存溢出
                //以下的两种都是执行目标类的方法
                //Object obj = methodProxy.invokeSuper(proxy, args);//执行目标类的方法
                Object obj=method.invoke(target, args);


                return obj;
            }

        };

        enhancer.setCallback(callback);
        return enhancer.create();   
    }
}
1. The difference between jdk dynamic proxy and cglib dynamic proxy

jdk: first have the object of the class that implements the interface, and then proxy the object
cglib: as long as there is a class (whether it implements the interface or not), the proxy for the class is simply to generate a subclass for the specified class and override the methods in it (inherit)

2.jdk dynamic proxy and cglib dynamic proxy in spring

(1) When the Bean implements the interface, Spring uses the jdk dynamic proxy by default
(2) When the Bean does not implement the interface, Spring uses the cglib dynamic proxy
(3) If the Bean implements the interface, it can also be forced to use the cglib dynamic proxy (in the spring configuration join `)

3. Pay attention

Use cglib to implement dynamic proxy. The bottom layer of cglib uses ASM bytecode generation framework, and uses bytecode technology to generate proxy classes, which is more efficient than using Java reflection. The only thing to note is that cglib cannot proxy methods declared as final, because the principle of cglib is to dynamically generate subclasses of the proxied class (classes modified by final cannot be inherited).

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325907340&siteId=291194637