CGLIB的动态代理与JDK原则
1、jdk动态代理
利用拦截器(拦截器必须实现InvocationHanlder)和反射机制,来生成实现代理接口的匿名类,
InvokeHandler在调用具体方法之前被调用。
2、cglb型动态代理
利用ASM的开源程序包,将代理对象类的class文件装载在其中,并通过修改它们的字节码来生成子类。
3、JDK或CGLIB什么时候使用?
1) JDK的动态代理默认用于在目标对象实现接口时实现AOP。
2) 当目标对象实现接口时,AOP可以通过CGLIB强制实现。
3) 若目标物件的介面未被执行,必须使用CGLIB库,Spring会自动在JDK动态代理与CGLIB之间转换。
4、我怎样使用CGLIB实现AOP?
(1) 增加CGLIB库(aspectjrt-xxx.jar,aspectjweaver-xxx.jar,cglib-nodep-xxx.jar)
(2) 添加到Spring概要
5、在JDK和CGLIB代码生成字节码之间有什么不同?
1)只有已经实现了接口的类才能生成JDK动态代理,而对于类则不行。
2)CGLIB实现类的代理,主要是为指定的类生成子类,并覆盖子类的方法,重新编写方法实现增强的部分,但是由于类或方法采用继承,所以最好不要声明为final,无法继承final类或方法。
6、cglib是否比JDK快?
1)利用CGLib实现了动态代理,并在CGLib的底层使用了ASM的字节码生成框架,生成了相应的代理类,
jdk6以前比Java反射更有效。唯一需要注意的是,CGLib不能代理声明为final的方法,
根据CGLib的原理,可以动态生成代理类的子类。
2)jdk6,jdk7,jdk8和jdk8在逐步优化JDK动态代理之后比CGLIB代理更高效,因为调用次数更少;
只有当进行大量调用时,jdk6和jdk7的效率才会低于CGLIB代理,但jdk8比CGLIB代理更有效,
总之,jdk代理的效率随着jdk版本的升级而提高,并且CGLIB代理消息也没有跟上。
斯普林如何使用JDK或CGLIB?
7、Spring在Bean实现接口时使用JDK的动态代理
1)如果Bean没有实现接口,Spring就会使用CGlib作为实现
2)可以强制CGlib(添加到spring配置中)