java反射机制 及 Method.invoke,Class. getMethod()的使用

来源:互联网 发布:成都市广电网络分公司 编辑:程序博客网 时间:2024/05/27 14:13

Java反射机制

JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。

Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类;在运行时构造任意一个类的对象;在运行时判断任意一个类所具有的成员变量和方法;在运行时调用任意一个对象的方法;生成动态代理。

Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类;在运行时构造任意一个类的对象;在运行时判断任意一个类所具有的成员变量和方法;在运行时调用任意一个对象的方法;生成动态代理。

Class


众所周知Java有个Object 类,是所有Java 类的继承根源,其内声明了数个应该在所有Java 类中被改写的方法:hashCode()、equals()、clone()、toString()、getClass()等。其中getClass()返回一个Class 对象。
Class 类十分特殊。它和一般类一样继承自Object,其实体用以表达Java程序运行时的classes和interfaces,也用来表达enum、array、primitive Java types(boolean, byte, char, short, int, long, float, double)以及关键词void。当一个class被加载,或当加载器(class loader)的defineClass()被JVM调用,JVM 便自动产生一个Class 对象。如果您想借由“修改Java标准库源码”来观察Class 对象的实际生成时机(例如在Class的constructor内添加一个println()),这样是行不通的!因为Class并没有public constructor。
1. 得到某个对象的属性
[java] view plain copy
  1. public Object getProperty(Object owner, String fieldName) throws Exception {    
  2.      Class ownerClass = owner.getClass();    
  3.      
  4.      Field field = ownerClass.getField(fieldName);    
  5.      
  6.      Object property = field.get(owner);    
  7.      
  8.      return property;    
  9. }    
Class ownerClass = owner.getClass():得到该对象的Class。
Field field = ownerClass.getField(fieldName):通过Class得到类声明的属性。
Object property = field.get(owner):通过对象得到该属性的实例,如果这个属性是非公有的,这里会报IllegalAccessException。
2. 得到某个类的静态属性
[java] view plain copy
  1. public Object getStaticProperty(String className, String fieldName)    
  2.              throws Exception {    
  3.      Class ownerClass = Class.forName(className);    
  4.      
  5.      Field field = ownerClass.getField(fieldName);    
  6.      
  7.      Object property = field.get(ownerClass);    
  8.      
  9.      return property;    
  10. }    
Class ownerClass = Class.forName(className) :首先得到这个类的Class。
Field field = ownerClass.getField(fieldName):和上面一样,通过Class得到类声明的属性。

Object property = field.get(ownerClass) :这里和上面有些不同,因为该属性是静态的,所以直接从类的Class里取。

3. 执行某对象的方法

Class[] e3 = new Class[]{Context.class, JSONObject.class, arguments.getClass()};Method t1 = page.getClazz().getMethod("openGMU", e3);Object[] args = new Object[]{context, gmuParams2, arguments};t1.invoke((Object)null, args);

[java] view plain copy
  1. public Object invokeMethod(Object owner, String methodName, Object[] args) throws Exception {    
  2.      
  3.      Class ownerClass = owner.getClass();    
  4.      
  5.      Class[] argsClass = new Class[args.length];    
  6.      
  7.      for (int i = 0, j = args.length; i < j; i++) {    
  8.          argsClass[i] = args[i].getClass();    
  9.      }    
  10.     
  11.       Method method = ownerClass.getMethod(methodName,argsClass);    
  12.      
  13.      return method.invoke(owner, args);    
  14. }    

Class owner_class = owner.getClass() :首先还是必须得到这个对象的Class。
for循环:配置参数的Class数组,作为寻找Method的条件。
Method method = ownerClass.getMethod(methodName, argsClass):通过methodName和参数的argsClass(方法中的参数类型集合)数组得到要执行的Method。
method.invoke(owner, args):执行该Method.invoke方法的参数是执行这个方法的对象owner,和参数数组args,可以这么理解:owner对象中带有参数args的method方法。返回值是Object,也既是该方法的返回值。

    4. 执行某个类的静态方法

[java] view plain copy
  1. public Object invokeStaticMethod(String className, String methodName,    
  2.              Object[] args) throws Exception {    
  3.      Class ownerClass = Class.forName(className);    
  4.      
  5.      Class[] argsClass = new Class[args.length];    
  6.      
  7.      for (int i = 0, j = args.length; i < j; i++) {    
  8.          argsClass[i] = args[i].getClass();    
  9.      }    
  10.      
  11.     Method method = ownerClass.getMethod(methodName,argsClass);    
  12.      
  13.      return method.invoke(null, args);    
  14.  }    
基本的原理和实例3相同,不同点是最后一行,invoke的一个参数是null,因为这是静态方法,不需要借助实例运行。

5. 新建实例

[java] view plain copy
  1. public Object newInstance(String className, Object[] args) throws Exception {    
  2.      Class newoneClass = Class.forName(className);    
  3.      
  4.      Class[] argsClass = new Class[args.length];    
  5.      
  6.      for (int i = 0, j = args.length; i < j; i++) {    
  7.          argsClass[i] = args[i].getClass();    
  8.      }    
  9.      
  10.      Constructor cons = newoneClass.getConstructor(argsClass);    
  11.      
  12.      return cons.newInstance(args);    
  13.      
  14. }    
这里说的方法是执行带参数的构造函数来新建实例的方法。如果不需要参数,可以直接使用newoneClass.newInstance()来实现。
Class newoneClass = Class.forName(className):第一步,得到要构造的实例的Class。
for循环:得到参数的Class数组。
Constructor cons = newoneClass.getConstructor(argsClass):得到构造子。
cons.newInstance(args):新建实例。

6. 判断是否为某个类的实例

[java] view plain copy
  1. public boolean isInstance(Object obj, Class cls) {    
  2.      return cls.isInstance(obj);    
  3. }    
7. 得到数组中的某个元素
[java] view plain copy
  1. public Object getByArray(Object array, int index) {     
  2.      return Array.get(array,index);     
  3. }    

参考文章:http://blog.csdn.net/ff313976/article/details/7931491

阅读全文
0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 被虚拟电话骚扰怎么办 一直有电话骚扰怎么办 老打电话骚扰我怎么办 总有电话骚扰怎么办 狗一直抽搐不停怎么办 右眼皮一直抽搐怎么办 打包机不停的倒带不切带怎么办 频繁被电话骚扰怎么办 一直被骚扰电话怎么办 有电话短信骚扰怎么办 收到大量验证码怎么办? 每天有陌生电话怎么办 电话不停被骚扰怎么办 水龙头的乱溅怎么办 水龙头坏了喷水怎么办 水龙头水流很散怎么办 自来水往外喷水怎么办 手机有骚扰电话怎么办 半夜到南宁机场怎么办 得了水痘坐火车怎么办 香港账户被限制怎么办 司法拍卖车扣分怎么办 速递易已超期怎么办 e栈快递换微信怎么办 e栈快递柜打不开怎么办 小孩耳朵塞东西怎么办 把隐形眼镜吃了怎么办 街道分车位不公平怎么办 服务区修车被宰怎么办 2018高速逃费怎么办 高速不停车卡怎么办 独立显卡显存不够怎么办 rx470d买不到了怎么办? 南方避险基金到期怎么办 高铁票认证失败怎么办 高铁票三个小孩怎么办 12306取消三次后怎么办 外国人护照过期了怎么办 行李丢飞机上怎么办 学生票没次数了怎么办 去美国行李超重怎么办