JAVA 动态代理 和 反射

       最近工作中接触到了JAVA的动态代理模式;其原理是利用JAVA的反射机制在程序运行时去生成代理类,动态代理相比静态代理的好处是当需要被代理的类数量较多时,可以减少在程序开发阶段预先定义大量的代理类,而把生成代理类的工作放在程序运行阶段让JVM处理。

       静态代理在AIDL开发中会用到,AIDL服务端程序定义好接口,然后AIDL客户端程序通过代理类调用服务端程序的接口达到通信的目的。

       目前接触到的动态代理是在 MVVM开发模式下,消息发送者通过callback代理类将消息传递给 真实callback类,最后传递给接收者;由于callback数量非常多,所以使用动态代理,代码如下:

Proxy.newProxyInstance(

target.getClass().getClassLoader(), target.getClass().getInterfaces(), new InvocationHandler() {

@Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable

{ return null; } })

其中targe为需要被代理的类,动态代理实现的核心是InvocationHandler 类。

       动态代理中用到的核心技术是反射和多态;记得刚学习JAVA时老师讲解过JAVA中的private属性的变量和方法并不是不能被其他类访问和修改,实现的方法是通过反射。

        即程序在运行时当JVM首次执行到 new 一个对象时,例如 Person person  = new Person(); 

        这时JVM会去加载编译好的 Person.class文件并生成一个Class 对象;一个类只有一个Class对象,反射的本质即是通过这个Class对象反向获取Person 对象的信息.

        反射的代码示例, 假设Person类的 id 属性是私有的,通过下面的代码可以改变id属性:

        Class personClazz = Class.forName("Person");

        Person person = personClazz.newInstance();

        Filed  id = personClazz.getDeclaredFiled("id");      

         id.setAccesible(true);

         id.set(person,1);

        多态是在程序开发阶段定义一个父类或父接口,在开发阶段传入了父类变量,在程序运行阶段JVM会动态加载子类,并调用子类的相关属性和函数。

        总结:当某些类不希望直接被暴露给其他类获程序操作时,可以使用代理模式;当需要被代理的类数量较少时可以使用静态代理,而如果数量较大时应该使用动态代理,动态代理的原理是JAVA程序在运行时JVM可以获取到父类引用所指向的子类对象所属类的信息。

发布了11 篇原创文章 · 获赞 2 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/zhengyin_tmac/article/details/104961857