快速业务通道

Java编程的动态性,第8部分: 用代码生成取代反射 - 编程入门网

作者 佚名技术 来源 NET编程 浏览 发布时间 2012-06-17
(incr)});        // print the ending values        System.out.println("Result values " +          bean.getValue1() + ", " + bean.getValue2());      } else {        System.out.println("Usage: ReflectAccess value1|value2");      }    } }

下面是运行 ReflectAccess 的两个例子,用来展示结果:

[dennis]$ java -cp . ReflectAccess value1 Result values 1, 0 [dennis]$ java -cp . ReflectAccess value2 Result values 0, 1

Java编程的动态性,第8部分: 用代码生成取代反射(2)

时间:2011-04-09 IBM Dennis M. Sosnoski

构建 glue 类

我已经展示了反射版本的代码,现在要展示如何用生成的类来取代反射。要想让这种取代 可以正确工作,会涉及到一个微妙的问题,它可追溯到本系列 第 1 部分中对类装载的讨论 。这个问题是:我想要在运行时生成一个可从访问类的静态编译的代码进行访问的类,但是 因为对编译器来说生成的类不存在,因此没办法直接引用它。

那么如何将静态编译的代码链接到生成的类呢?基本的解决方案是定义可以用静态编译的 代码访问的基类或者接口,然后生成的类扩展这个基类或者实现这个接口。这样静态编译的 代码就可以直接调用方法,即使方法只有到了运行时才能真正实现。

在清单 2 中,我定义了一个接口 IAccess ,目的是为生成的代码提供这种链接。这个接 口包括三个方法。第一个方法只是设置要访问的目标对象。另外两个方法是用于访问一个 int 属性值的 get 和 set 方法的代理。

清单 2. 到 glue 类的接口

public interface IAccess {    public void setTarget(Object target);    public int getValue();    public void setValue(int value); }

这里的意图是让 IAccess 接口的生成实现提供调用目标类的相应 get 和 set 方法的代 码。清单 3 显示了实现这个接口的一个例子,假定我希望访问 清单 1 中 HolderBean 类的 value1 属性:

清单 3. Glue 类示例实现

public class AccessValue1 implements IAccess {    private HolderBean m_target;    public void setTarget(Object target) {      m_target = (HolderBean)target;    }    public int getValue() {      return m_target.getValue1();    }    public void setValue(int value) {      m_target.setValue1(value);    } }

清单 2 接口设计为针对特定类型对象的特定属性使用。这个接口使实现代码简单了 —— 在处理字节码时这总是一个优点 —— 但是也意味着实现类是非常特定的。对于要通过这个 接口访问的每一种类型的对象和属性,都需要一个单独的实现类,这限制了将这种方法作为 反射的一般性替代方法。如果选择只在反射性能真正成为瓶颈的情况下才使用这种技术,那 么这种限制就不是一个问题。

用 Javassist 生成

用 Javassist 为 清单 2 IAccess 接口生成实现类很容易 —— 只需要创建一个实现了 这个接口的新类、为目标对象引用添加一个成员变量、最后再添加一个无参构造函数和简单 实现方法。清单 4 显示了完成这些步骤的 Javassist 代码,它构造一个方法调用,这个方 法以目标类和 get/set 方法信息为参数、并返回所构造的类的二进制表示:

清单 4. Javassist glue 类构造

/** Parameter types for call with no parameters. */ private static final CtClass[] NO_ARGS = {}; /** Parameter types for call with single int value. */ private static final CtClass

凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!

分享到: 更多

Copyright ©1999-2011 厦门凌众科技有限公司 厦门优通互联科技开发有限公司 All rights reserved

地址(ADD):厦门软件园二期望海路63号701E(东南融通旁) 邮编(ZIP):361008

电话:0592-5908028 传真:0592-5908039 咨询信箱:web@lingzhong.cn 咨询OICQ:173723134

《中华人民共和国增值电信业务经营许可证》闽B2-20100024  ICP备案:闽ICP备05037997号