标签:and llb method nbsp 字节码 icp 文件 ceo java动态代理
代理模式的定义:为其他对象提供一种代理以控制对这个对象的访问。在某些情况下,一个对象不适合或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。
静态代理模式:由程序员自己创建代理类源码,再编译代理类。也就是程序运行前就已经存在代理类的字节码文件,代理类与委托类的关系在运行前就确定了。
抽象角色
public interface InterfaceObject { void sayHello(); }
目标角色
public class RealObject implements InterfaceObject{ public void sayHello() { System.out.println("Hello World..."); } }
代理角色
public class ProxyObject implements InterfaceObject{ private RealObject realObject; public ProxyObject(RealObject realObject){ this.realObject = realObject; } public void sayHello() { System.out.println("Before Hello World..."); realObject.sayHello(); System.out.println("After Hello World..."); } }
动态代理:在实现阶段不用关心代理类,而在运行阶段才指定是哪一个对象
JDK动态代理
public class ProxyInvocationHandler implements InvocationHandler{ private Object target;//对真实对象的引用 public ProxyInvocationHandler(Object target){ this.target = target; } public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { System.out.println("Before DynamicProxy..."); //执行方法... method.invoke(target,args); System.out.println("After DynamicProxy..."); return null; } }
//动态代理(JDK动态代理) InterfaceObject realObject = new RealObject();//目标对象 //创建与代理对象相关连的InvocationHandler InvocationHandler handler = new ProxyInvocationHandler(realObject); InterfaceObject proxy1 = (InterfaceObject) Proxy.newProxyInstance(InterfaceObject.class.getClassLoader(), new Class<?>[]{InterfaceObject.class}, handler); proxy1.sayHello();
底层原理:
查看源码Class<?> cl = getProxyClass0(loader, intfs);产生了代理类$Proxy0 extends Proxy implements InterfaceObject(存放在内存中)
发编译查看代理类的构造方法调用了父类Proxy的构造方法super(paramInvocationHandler);
protected Proxy(InvocationHandler h) { Objects.requireNonNull(h); this.h = h; }
静态代码块得到了代理方法 m3 = Class.forName("proxy.InterfaceObject").getMethod("sayHello", new Class[0]);
代理类的sayHello()方法直接调用了InvocationHandler中的invoke方法,并把m3传了进去this.h.invoke(this, m3, null);
代理类继承了Proxy类,所以Java动态代理只能对接口进行代理(java不支持多继承)
cglib动态代理
public class ProxyInterceptor implements MethodInterceptor{ public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable { proxy.invokeSuper(obj, args); return null; } }
//cglib动态代理 Enhancer enhancer = new Enhancer(); enhancer.setSuperclass(RealObject.class); enhancer.setCallback(new ProxyInterceptor()); RealObject realObject2 = (RealObject) enhancer.create(); realObject2.sayHello();
cglib利用继承的方式动态创建了被代理类的子类,通过ASM生成父类中所有public非final修饰的方法,实现了代理
invokeSuper方法以fastclass这种非反射机制快速的调用到代理类中的方法
标签:and llb method nbsp 字节码 icp 文件 ceo java动态代理
原文地址:https://www.cnblogs.com/panda28/p/10594701.html