java反射系七之动态代理
一.概念认知
静态代理:
package staticProxy; //静态代理模式 //接口 interface ClothFactory{ void productCloth(); } //创建被代理类 class NikeClothFactory implements ClothFactory{ @Override public void productCloth() { System.out.println("Nike生产了一批衣服"); } } //创建代理类 class ProxyFactory implements ClothFactory{ ClothFactory cf; public ProxyFactory(ClothFactory cf) { this.cf=cf; } @Override public void productCloth() { System.out.println("收取代理费1000$"); cf.productCloth(); } }
动态代理:
package staticProxy; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; //动态代理的使用 interface Subject{ void action(); } //被代理类 class RealSubject implements Subject{ @Override public void action() { System.out.println("我是被代理类,么么哒~"); } } //凡是涉及到动态代理的都要实现InvocationHandler接口 class MyInvocationHandler implements InvocationHandler{ //实现了接口的被代理类的对象的声明 Object obj; public Object blind(Object obj) { this.obj=obj; /* * obj.getClass().getClassLoader()-->和被代理类的加载器一致 * obj.getClass().getInterfaces()-->和被代理类的实现接口一致 * this-->代表MyInvocationHandler * 1.给被代理的对象实例化;2.返回一个代理类的对象 */ return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), this); } //当通过代理类的对象发起被重写的方法的调用时,都会转化为对如下的invoke方法的调用 @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { //method方法的返回值是returnValue Object returnValue = method.invoke(obj, args); return returnValue; } } public class TestProxy { public static void main(String[] args) { //1.被代理类的对象 RealSubject real = new RealSubject(); //2.创建一个实现了InvacationHandler接口的类的对象 MyInvocationHandler handler = new MyInvocationHandler(); //3.调用blind()方法,动态的返回一个同样实现了real所在类实现的接口Subject的代理类的对象 Object obj = handler.blind(real); //此时sub就是代理类的对象 Subject sub = (Subject)obj; //转到对InvacationHandler接口的实现类的invoke方法的调用 sub.action(); /* * 程序分析:blind方法使得代理类实现了和被代理类一样的接口 * 所以返回的是代理类对象 * 所以可以调用接口方法 * 而此时调用接口方法又会转化为invoke方法 * invoke方法中替换成被代理类对象 */ //举个栗子 NikeClothFactory nike = new NikeClothFactory(); //实现了ClothFactory接口,返回的是Object,这里强制转型,返回的是代理类对象 ClothFactory pro = (ClothFactory)handler.blind(nike); //调用接口方法,转换为invoke方法,替换成nike对象 pro.productCloth(); } }
你们看懂了嘛?反正我是懂了,接下来只需要练习,哈哈,我可真是个小机灵鬼