Java反射机制的实现原理

反射机制:所谓的反射机制就是java语言在运行时拥有一项自观的能力。通过这种能力可以彻底的了解自身的情况为下一步的动作做准备。下面具体介绍一下java的反射机制。这里你将颠覆原来对java的理解。

Java的反射机制的实现要借助于4个类:class,Constructor,Field,Method;其中class代表的时类对象,Constructor-类的构造器对象,Field-类的属性对象,Method-类的方法对象。通过这四个对象我们可以粗略的看到一个类的各个组成部分。

Class:程序运行时,java运行时系统会对所有的对象进行运行时类型的处理。这项信息记录了每个对象所属的类,虚拟机通常使用运行时类型信息选择正确的方法来执行(摘自:白皮书)。但是这些信息我们怎么得到啊,就要借助于class类对象了啊。在Object类中定义了getClass()方法。我们可以通过这个方法获得指定对象的类对象。

Java反射机制主要提供了以下功能:

1.在运行时判断任意一个对象所属的类。

2.在运行时构造任意一个类的对象。

3.在运行时判断任意一个类所具有的成员变量和方法。

4.在运行时调用任意一个对象的方法。

Reflection是Java被视为动态(或准动态)语言的一个关键性质。

这个机制允许程序在运行时透过Reflection APIs取得任何一个已知名称的class的内部信息。

包括其modifiers(诸如public、static等)、 superclass(例如Object)、实现了的 interfaces (例如Serializable)、也包括其fields和methods的所有信息,并可于运行时改变fields内容或调用methods。

然后我们通过分析这个对象就可以得到我们要的信息了。

比如:ArrayList arrayList;

Class clazz = arrayList.getClass();

然后我来处理这个对象clazz。

当然了Class类具有很多的方法,这里重点将和Constructor,Field,Method类有关系的方法。

Reflection 是 Java 程序开发语言的特征之一,它允许运行中的 Java 程序对自身进行检查,或者说“自审”,并能直接操作程序的内部属性。Java 的这一能力在实际应用中也许用得不是很多,但是个人认为要想对java有个更加深入的了解还是应该掌握的。

1.检测类:

reflection的工作机制

考虑下面这个简单的例子,让我们看看 reflection 是如何工作的。

import java.lang.reflect.Method;

public class DumpMethods {

public static void main(String args[]) {

try {

Class c = Class.forName(args[0]);

Method m[] = c.getDeclaredMethods();

for (int i = 0; i < m.length; i++)

System.out.println(m[i].toString());

} catch (Throwable e) {

System.err.println(e);

}

}

}

按如下语句执行:

java DumpMethods java.util.ArrayList

这个程序使用 Class.forName 载入指定的类,然后调用 getDeclaredMethods 来获取这个类中定义了的方法列表。java.lang.reflect.Methods 是用来描述某个类中单个方法的一个类。

Java类反射中的主要方法

对于以下三类组件中的任何一类来说 -- 构造函数、字段和方法 -- java.lang.Class 提供四种独立的反射调用,以不同的方式来获得信息。调用都遵循一种标准格式。以下是用于查找构造函数的一组反射调用:

Constructor getConstructor(Class[] params) -- 获得使用特殊的参数类型的公共构造函数,

Constructor[] getConstructors() -- 获得类的所有公共构造函数

Constructor getDeclaredConstructor(Class[] params) -- 获得使用特定参数类型的构造函数(与接入级别无关)

Constructor[] getDeclaredConstructors() -- 获得类的所有构造函数(与接入级别无关)

获得字段信息的Class 反射调用不同于那些用于接入构造函数的调用,在参数类型数组中使用了字段名:

Field getField(String name) -- 获得命名的公共字段

Field[] getFields() -- 获得类的所有公共字段

Field getDeclaredField(String name) -- 获得类声明的命名的字段

Field[] getDeclaredFields() -- 获得类声明的所有字段

用于获得方法信息函数:

Method getMethod(String name, Class[] params) -- 使用特定的参数类型,获得命名的公共方法

Method[] getMethods() -- 获得类的所有公共方法

Method getDeclaredMethod(String name, Class[] params) -- 使用特写的参数类型,获得类声明的命名的方法

Method[] getDeclaredMethods() -- 获得类声明的所有方法

使用 Reflection:

用于 reflection 的类,如 Method,可以在 java.lang.relfect 包中找到。使用这些类的时候必须要遵循三个步骤:第一步是获得你想操作的类的 java.lang.Class 对象。在运行中的 Java 程序中,用 java.lang.Class 类来描述类和接口等。

下面就是获得一个 Class 对象的方法之一:

Class c = Class.forName("java.lang.String");

这条语句得到一个 String 类的类对象。还有另一种方法,如下面的语句:

Class c = int.class; 或者  Class c = Integer.TYPE;

它们可获得基本类型的类信息。其中后一种方法中访问的是基本类型的封装类 (如 Intege ) 中预先定义好的 TYPE 字段。

第二步是调用诸如 getDeclaredMethods 的方法,以取得该类中定义的所有方法的列表。

一旦取得这个信息,就可以进行第三步了——使用 reflection API 来操作这些信息,如下面这段代码:

Class c = Class.forName("java.lang.String");

Method m[] = c.getDeclaredMethods();

System.out.println(m[0].toString());

它将以文本方式打印出 String 中定义的第一个方法的原型。

处理对象:

a.创建一个Class对象

b.通过getField 创建一个Field对象

c.调用Field.getXXX(Object)方法(XXX是Int,Float等,如果是对象就省略;Object是指实例).

例如:

import java.lang.reflect.*;

import java.awt.*;

public class SampleGet {

public static void main(String[] args) {

Rectangle r = new Rectangle(100, 325);

printHeight(r);

}

static void printHeight(Rectangle r) {

Field heightField;

Integer heightValue;

Class c = r.getClass();

try {

heightField = c.getField("height");

heightValue = (Integer) heightField.get(r);

System.out.println("Height: " + heightValue.toString());

} catch (NoSuchFieldException e) {

System.out.println(e);

} catch (SecurityException e) {

System.out.println(e);

} catch (IllegalAccessException e) {

System.out.println(e);

}

}

}

生成对象

1.先获得Class对象,然后通过该Class对象的newInstance()方法直接生成即可:

Class> classType = String.class;

Object obj = classType.newInstance();

2.先获得Class对象,然后通过该对象获得对应的Constructor对象,再通过该Constructor对象的newInstance()方法生成(其中Customer是一个自定义的类,有一个无参数的构造方法,也有带参数的构造方法):

Class> classType = Customer.class;

// 获得Constructor对象,此处获取第一个无参数的构造方法的

Constructor cons = classType.getConstructor(new Class[] {});

// 通过构造方法来生成一个对象

Object obj = cons.newInstance(new Object[] {});

3.若想通过类的带参数的构造方法生成对象,只能使用下面这一种方式:

(Customer为一个自定义的类,有无参数的构造方法,也有一个带参数的构造方法,传入字符串和整型)

Class> classType = Customer.class;

Constructor cons2 = classType.getConstructor(new Class[] {String.class, int.class});

Object obj2 = cons2.newInstance(new Object[] {"ZhangSan",20});

可以看出调用构造方法生成对象的方法和调用一般方法的类似,不同的是从Class对象获取Constructor对象时不需要指定名字,而获取Method对象时需要指定名字

工作中用到的java反射机制_(转)JAVA-反射机制的使用相关推荐

  1. java反射实例_关于java反射的一个案例

    案例: *需求:"写一个框架",可以帮我们创建任意类的对象,并且执行其中任意的方法. *实现: 1.配置文件 2.反射 *步骤: 1.将需要创建的对象的全类名和需要执行的方法定义在 ...

  2. java实现分发_关于JAVA中事件分发和监听机制实现的代码实例

    [实例简介] 关于JAVA中事件分发和监听机制实现的代码实例,绝对实用代码,有说明. [实例截图] [核心代码] JavaEventDispatch ├── bin │   └── com │   └ ...

  3. java动态类加载_实现Java动态类载入机制

    作 为 充 分 利 用Java 的 动 态 类 载 入 机 制 的 最 好 例 子, 带 有Java 扩 展 的Web 浏 览 器 根 据 请 求 从 网 络 或 本 地 文 件 系 统 中 动 态 ...

  4. 达内学java要多久_自学Java需要学多久才能达到工作的程度

    目前Java以上IT市场中最受企业欢迎的开发语言,所以很多人想自学Java,学精通后转行做Java开发类的工作.今天小编就来给大家讲讲自学Java需要学多久才能达到工作的程度. 其实不同的人学习Jav ...

  5. java初始化数据报_初始化java原因

    虚拟机的类加载机制 虚拟机把描述类的数据从Class文件加载到内存,并对数据进行校验.转换解析和初始化,最终形成可以被虚拟机直接使用的Java类 即虚拟机的类加载机制. 在Java中,类型的加载.链接 ...

  6. java面向对象课件_《JAVA面向对象基础》PPT课件.ppt

    <<JAVA面向对象基础>PPT课件.ppt>由会员分享,可在线阅读,更多相关<<JAVA面向对象基础>PPT课件.ppt(68页珍藏版)>请在人人文库 ...

  7. java 分割一个_分割java

    [java]分割字符串工具类,霸气 jdk自带的 java 分割字符串,分割string,可以根据多个条件去分割.比如逗号,分号,逗号或者分号. 比如一个字符串:"abc,def;gh,ij ...

  8. java 字符串包_包java字符串

    Java核心技术卷I基础知识3.6.3 不可变字符串 3.6.3 不可变字符串 String类没有提供用于修改字符串的方法.如果希望将greeting的内容修改为"Help!",不 ...

  9. java高级教程_高级Java教程

    java高级教程 课程大纲 学习Java基础很容易. 但是,真正钻研该语言并研究其更高级的概念和细微差别将使您成为一名出色的Java开发人员. 网络上充斥着"软","便宜 ...

最新文章

  1. 【Redfin SDE intern】跪经
  2. 手把手教你上手python库pydbgen(附代码、安装地址)
  3. MySQL的binlog日志
  4. 量子导航即将上路:实时更新,全局优化,不仅更快还能解决拥堵
  5. sql server 2008 远程连接配置
  6. 低开销、简单的网站监控工具Checkless开发者专访
  7. peewee mysql自动断开_flask+mako+peewee(下)(解决了Error 2006: MySQL server has gone away)
  8. python免费网课-Python网课推荐——免费学习Python编程
  9. BATJ等大厂最全经典面试题分享
  10. 无法写入最后一个_手机资讯:iPhone 扩容机能否进行刷机刷机后无法激活怎么办...
  11. Gsonformat
  12. COMMUNITY DETECTION
  13. 【算力网络白皮书学习】
  14. matlab读取视频VideoRead用法
  15. Windows10修改Users下的用户文件夹名
  16. 我的世界服务器修改皮肤指令,我的世界怎么拿指令来改皮肤的 | 手游网游页游攻略大全...
  17. 数据分析师的发展前景
  18. 【Linux】awk文本替换
  19. 您如何用leetcode进行面试很不好
  20. OGC PUCK协议标准版本v1.4 翻译

热门文章

  1. python 爬虫源代码-从零开始学Python网络爬虫_源代码.rar
  2. python 文件读写找不到文件-python之文件读写
  3. python第三方库有哪些-我常用的几个第三方 Python 库
  4. 怎样学好python-如何学好python——致python初学者的天梯
  5. python基础语法第10关作业-【python基础语法】第8天作业练习题
  6. python编程入门与案例详解pdf-Python爬虫天气预报实例详解(小白入门)
  7. python中文意思k-【Python】 汉字转化汉语拼音pinyin
  8. python怎么导入文本-如何导入其他Python文件?
  9. Linux实用命令大合集(长期更新)
  10. python 学习