demo
//被代理类不需要实现接口(与jdk动态代理的区别)
public class YunZhongYu {
public void findLove(){
System.out.println("-------------");
}
}
public class YustMeipo implements MethodInterceptor {
//疑问:好像并没有持有被代理对象的引用,见下个方法的注释
public Object getInstance(Class clazz) throws Exception{
Enhancer enhancer = new Enhancer();
//创建一个类,设置它的父类为我们的代理对象
enhancer.setSuperclass(clazz);
//这里把this传进去,是为了回调本对象的 intercept 方法,(25行下面那个方法)
enhancer.setCallback(this);
//1.生成源代码
//2.编译成class文件
//3.加载到JVM,并返回代理对象
return enhancer.create();
}
@Override
public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
System.out.println("------------");
//这个obj的引用是cglib给我们new出来的。
//cglib new 出来以后的对象,是被代理对象的子类(继承了我们自己写的那个类
// OOP:在new出子类之前,实际上默认调用了我们的super()方法的
// ,new 了子类的同事,必须先new出父类,这就相当于间接的持有了我们的父类的引用
//子类重写了父类的所有方法
//我们改变了子类对象的某些属性,是可以间接的操作父类的属性的
//这里调用父类的findLove方法,如果这里调用子类的findLove方法会造成死循环。
//如果这里调用子类的findLove方法: 因为 obj是子类的引用。 test类中 obj.findLove();每次调用这个方法就会回调intercept方法,intercept方法中又调用自己,这就循环调用了。
//如果这里调用父类的findLove方法:调用父类的findLove方法,就会执行我们父类中的 自己写的findLove方法,不会回调intercept方法。
proxy.invokeSuper(obj, args);
return null;
}
}
public class YustTestFindLove {
//JDK的动态代理是通过接口来进行强转的。
//生成以后的代理对象,可以强转为接口
//CGLib的动态代理是通过生成一个被代理对象的子类,然后重写父类方法,
//生成以后的对象,可以强转为被代理对象(也就是自己写的类)
//子类引用赋值给父类
public static void main(String[] args){
try {
YunZhongYu obj = (YunZhongYu)new YustMeipo().getInstance(YunZhongYu.class);
obj.findLove();
} catch (Exception e) {
e.printStackTrace();
}
}
}
网友评论