黑马程序员 代理学习
来源:互联网 发布:淘宝原单男装店铺 编辑:程序博客网 时间:2024/05/17 07:29
----------- android培训、java培训、期待与您交流! ------------
代理
生活中,消费者与厂商之间有代理商。代理商提供了一定的功能,如:将货物送到消费者手中,保鲜等
程序中,也有类似的中间件-代理类。
代理类:与目标类有相同的接口(方法集合),代理中的每个方法都调用目标类的方法,提供了一些附加的功能,如计算方法的运行时间,异常处理、事务管理、日志等。
具体应用:如果采用工厂模式和配置文件的方式进行管理,在配置文件中配置是使用目标类,还是代理类,很方便的进行切换。同时以后若想去掉附加的功能,也很方便。
示例代码
class A {//目标类void method() {}}class XProxy {//代理类void method() {//和目标类有相同的方法startTime;//增加系统功能A.method();//调用目标类的方法endTime;//增加系统功能}}
代理架构图:
AOP
代理是实现AOP功能的核心和关键技术。
那什么是AOP?
答:Aspect oriented program,面向方面编程。
什么是交叉业务?
答:安全、事务、日志等功能要贯穿到很多个模块中,它们就是交叉业务。
AOP的目标:使交叉业务模块化。
如何实现的?
答:采用将切面代码移动到原始方法的周围。这与直接在方法中编写切面面代码是一样的。(这里的切面代码:就是附加的功能代码)
实际开发中,将切面代码封装成对象,传递给InvocationHandler的invoke()方法。
动态代理技术
要为系统中的各种接口的类增加代理功能,若全部采用静态代理的方式,将需要很多的代理类。
动态代理类:JVM可以在运行时期动态的生成类的字节码,这种动态生成的类往往被用作代理类,即动态代理类。
JVM生成的动态类必须实现一个或多个接口,所以其只能代理于具有相同接口的目标类。
CGLIB库:可以动态生成一个类的子类,一个类的子类也可作为此类的代理,所以要为一个没有实现接口的类生成代理,可以用CGLIB库。(是一个插件)
系统功能代码(切面代码)存放于代理方法中的位置:1、调用的目标方法前;2、调用的目标方法后;3、代理方法的异常处理的catch块中。
JVM动态生成类的字节码:实例代码
动态生成一个实现了Collection接口的类字节码,并使用反射技术查看这个动态类的一些内部信息。
import java.util.*;import java.lang.reflect.*;class ProxyDemo {public static void main(String[] args) {Class clazzProxy = Proxy.getProxyClass(Collection.class.getClassLoader(),Collection.class); //动态生成一个类System.out.println(clazzProxy.getName());System.out.println("----------构造方法:-------");Constructor[] constructors = clazzProxy.getConstructors();for(Constructor constructor : constructors) {System.out.println("构造方法:" + constructor);}System.out.println("----------普通方法:-------");Method[] methods = clazzProxy.getMethods();for(Method method : methods) {System.out.println("普通方法:" + method);Class[] clazzParams = method.getParameterTypes();for(Class clazzParam : clazzParams) {System.out.println("----参数为:" + clazzParam.getName());}Type[] types = method.getGenericExceptionTypes();for(Type type : types) {System.out.println("--------方法抛出的异常类型为:" + type);}}}}
创建动态代理类的实例对象,如下
Collection proxy3 = (Collection)Proxy.newProxyInstance(Collection.class.getClassLoader(),//第一个参数:用于产生动态类的接口的类加载器 new Class[]{Collection.class},//第二个参数:用于产生动态类的接口的类型数组 new InvocationHandler(){//第三个参数:实现了Invocation接口的匿名类对象ArrayList target = new ArrayList();//目标类对象public Object invoke(Object proxy, Method method, Object[] args) throws Throwable{ //动态代理类的方法调用函数long startTime = System.currentTimeMillis();Object retVal = method.invoke(target, args);//目标类方法调用函数long endTime = System.currentTimeMillis();System.out.println(method.getName() + "方法运行时间" + (endTime - startTime));return retVal;}});proxy3.add("Hello");proxy3.add("Java");System.out.println("集合元素个数:" + proxy3.size());}
InvocationHandler对象运行原理:
Client程序调用proxyObj.add("AB")方法时,涉及三要素:1、哪个对象调用的,proxyObj 2、调用的是哪个方法 3、调用方法的参数
调用的过程:调用用proxyMethod.invoke(),这个方法需要目标方法的返回值,它会自动去调用targetMethod.invoke(),然后将返回值传递给proxyMethod.invoke(),再传递给调用者;传值的过程中,代理类的附加代码也相继运行。
分析代理类的方法:
class Proxy$ {add(Object obj) {return handler.invoke(Object proxy, Method method, Object[] args)}int size() {return handler.invoke(this, this.getClass().getMethod("size"), null);}}
动态代理工作原理图:
----------------------- android培训、java培训、期待与您交流! ----------------------
详情请查看:
- 黑马程序员 代理学习
- 黑马程序员 动态代理学习笔记二
- 黑马程序员 动态代理学习笔记一
- 黑马程序员_Java 代理机制学习总结
- 黑马程序员-OC学习笔记-----协议、代理
- 黑马程序员 动态代理
- 黑马程序员--代理
- 黑马程序员-java-代理
- 黑马程序员_代理
- 黑马程序员_java代理
- 黑马程序员:代理
- 黑马程序员_代理
- 黑马程序员-代理
- 黑马程序员-动态代理
- 黑马程序员 动态代理
- 黑马程序员-动态代理
- 黑马程序员--动态代理
- 黑马程序员-代理
- 详细介绍Struts、Hibernate、Spring的原理以及优点
- C# 4.0新特性dynamic作用浅析
- php中,对象完全变成数组
- thrift的各种资料
- perl中 localtime和timelocal
- 黑马程序员 代理学习
- 修改树状控件TreeCtrl的节点名称
- 无法启动调试--未安装 Silverlight Developer 运行时。请安装一个匹配版本
- 苹果封锁“应用内购买”漏洞 黑客另出高招
- 拦截器和过滤器的区别
- XP使用技巧
- 探讨Ilist<>与List<>
- Icon specified in the Info.plist not found under the top level app wrapper:解决办法
- JList的用法