JDK 与 CGLib 动态代理

1. 区别

参考:JDK和CGLIB动态代理原理区别

  1. JDK动态代理只能对实现了接口的类生成代理,而不能针对类。
  2. CGLIB是针对类实现代理,主要是对指定的类生成一个子类,覆盖其中的方法,并覆盖其中方法实现增强,但是因为采用的是继承,所以该类或方法最好不要声明成final, 对于final类或方法,是无法继承的。

2. JDK 动态代理

参考:
1. jdk动态代理举例 == 使用
2. 深度剖析JDK动态代理机制 == 底层剖析

jdk动态代理举例:

public interface Say {
    void sayHello(String words);
}
public class SayImpl implements Say {
    @Override
    public void sayHello(String words) {
        System.out.println("hello:" + words);
    }
}
public class TestInvocationHandler implements InvocationHandler {

    private Object target;
    public TestInvocationHandler(Object target) {
        this.target=target;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("invoke begin");
        System.out.println("method :"+ method.getName()+" is invoked!");
        method.invoke(target,args);
        System.out.println("invoke end");
        return null;
    }
}
 public static void main(String[] args) {

        TestInvocationHandler testInvocationHandler = new TestInvocationHandler(new SayImpl());
        Say say = (Say)Proxy.newProxyInstance(SayImpl.class.getClassLoader(), SayImpl.class.getInterfaces(), testInvocationHandler );
        say.sayHello("my dear");
    }

打印输出:

invoke begin
method :sayHello is invoked!
hello:my dear
invoke end

3. CGLib 动态代理

参考:
1. CGLib动态代理原理及实现 == 使用
2. cglib源码分析(四):cglib 动态代理原理分析 == 底层剖析

CGLib 动态代理举例

public class SayHello {  
 public void say(){  
  System.out.println("hello everyone");  
 }  
}  
public class CglibProxy implements MethodInterceptor{  
 private Enhancer enhancer = new Enhancer();  
 public Object getProxy(Class clazz){  
  //设置需要创建子类的类  
  enhancer.setSuperclass(clazz);  
  enhancer.setCallback(this);  
  //通过字节码技术动态创建子类实例  
  return enhancer.create();  
 }  
 //实现MethodInterceptor接口方法  
 public Object intercept(Object obj, Method method, Object[] args,  
   MethodProxy proxy) throws Throwable {  
  System.out.println("前置代理");  
  //通过代理类调用父类中的方法  
  Object result = proxy.invokeSuper(obj, args);  
  System.out.println("后置代理");  
  return result;  
 }  
}  
public class DoCGLib {  
 public static void main(String[] args) {  
  CglibProxy proxy = new CglibProxy();  
  //通过生成子类的方式创建代理类  
  SayHello proxyImp = (SayHello)proxy.getProxy(SayHello.class);  
  proxyImp.say();  
 }  
} 

结果输出:

前置代理  
hello everyone  
后置代理  

猜你喜欢

转载自blog.csdn.net/yin__ren/article/details/80949049