Java 设计模式之代理模式
一、代理模式是什么?
代理是指为其它对象提供的一种代理,用以对这个对象访问的控制。通俗说就是代替别人去做我们想做的事件。
二、静态代理
抽象类:
1 public abstract class BaseObject { 2 3 protected abstract void operation(); 4 5 }
派生类:
1 public class RealObject extends BaseObject { 2 3 @Override 4 protected void operation() { 5 System.out.print("realobject operaion."); 6 } 7 8 }
代理类:
1 public class ProxyObject extends BaseObject { 2 3 private RealObject mRealObject; 4 5 public ProxyObject(RealObject realObject) { 6 mRealObject = realObject; 7 } 8 9 @Override 10 protected void operation() { 11 System.out.print("proxyobject begin."); 12 13 mRealObject.operation(); 14 15 System.out.print("proxyobject end."); 16 } 17 }
作用:对已有方法进行改进,可以使用静态代理完成,对产生结果进行控制,通过代理模式对功能划分更加清晰。
三、动态代理
动态代理类就是在程序运行时创建的代理方式。相比于静态代理,动态代理可以统一的对代理方法进行统一处理。
动态代理是面向接口的。
动态代理写法,支持动态代理的两个库:
- JDK动态代理,JDK动态代理是需要客户端写辅助接口,使用Java内部反射机制实现,在生成类的过程中比较高效;
- CGLIB动态代理,直接修改字节实现的;
接口类:
1 public interface Subject { 2 3 void doAction(); 4 5 }
被代理对象类:
1 public class RealObject implements Subject { 2 3 @Override 4 public void doAction() { 5 System.out.println("realobject doaction."); 6 } 7 8 }
动态代理类:
1 public class ProxyObject implements InvocationHandler { 2 3 private Object mTarget; 4 5 public ProxyObject(Object target) { 6 mTarget = target; 7 } 8 9 @Override 10 public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { 11 System.out.println("proxy: " + proxy.getClass().getName()); 12 System.out.println("begin"); 13 14 method.invoke(proxy, args); 15 16 System.out.println("end"); 17 18 return null; 19 } 20 21 }
使用方法:
1 Subject realObject = new RealObject(); 2 ProxyObject proxy = new ProxyObject(realObject); 3 Subject subject = (Subject) Proxy.newProxyInstance(realObject.getClass().getClassLoader() 4 , RealObject.getClass().getInterfaces(), proxy); 5 6 subject.doAction();
总结:
动态代理里主要有一个拦截概念,在动态代理每个代理类对象关联一个表示内部处理逻辑的InvocationHandler接口类实现。使用都调用代理类方法时,都会传递到这个InvocationHandler接口的invoke()方法。在invoke()方法中可以获取到代理对象、方法及参数。并且invoke()方法的返回值会被返回给使用者。
InvocationHandler接口类:
1 package java.lang.reflect; 2 3 public interface InvocationHandler { 4 Object invoke(Object var1, Method var2, Object[] var3) throws Throwable; 5 }
四、静态代理与动态代理区别
动态代理的代理类在运行时动态生成的,依据配置动态生成的代理类,这个生成的代理类已经实现了相关的代理接口,只要提供一个InvocationHandler并实现invoke()方法即可。