先从百度抄点定义来看
Java的反射(reflection)机制是指在程序的运行状态中,可以构造任意一个类的对象,可以了解任意一个对象所属的类,可以了解任意一个类的成员变量和方法,可以调用任意一个对象的属性和方法。这种动态获取程序信息以及动态调用对象的功能称为Java语言的反射机制。反射被视为动态语言的关键。
尽管反射机制带来了极大的灵活性及方便性,但反射也有缺点。反射机制的功能非常强大,但不能滥用。在能不使用反射完成时,尽量不要使用,原因有以下几点:
1、性能问题。
Java反射机制中包含了一些动态类型,所以Java虚拟机不能够对这些动态代码进行优化。因此,反射操作的效率要比正常操作效率低很多。我们应该避免在对性能要求很高的程序或经常被执行的代码中使用反射。而且,如何使用反射决定了性能的高低。如果它作为程序中较少运行的部分,性能将不会成为一个问题。
2、安全限制。
使用反射通常需要程序的运行没有安全方面的限制。如果一个程序对安全性提出要求,则最好不要使用反射。
3、程序健壮性。
反射允许代码执行一些通常不被允许的操作,所以使用反射有可能会导致意想不到的后果。反射代码破坏了Java程序结构的抽象性,所以当程序运行的平台发生变化的时候,由于抽象的逻辑结构不能被识别,代码产生的效果与之前会产生差异。
假设现在定义一个类Student,手动设置几个构造函数,为它封装一个private String name属性。我们将在之后使用它。
// 获取类信息的三种方式 // 1.从对象获取 Student stu = new Student(); Class class1 = stu .getClass(); // 2.从类获取 Class class2 = Student .class; // 3.使用forName()需要捕获ClassNotFoundException异常 Class class3 = Class.forName("demo.test.Student");
class1,class2,class3的输出结果均为"class demo.test.Student"。
Student stu = (Student)class1.newInstance();
Constructor[] class1Constructors = class1.getConstructors();
Field是一个类,位于Java.lang.reflect包下,在Java反射中Field用于获取某个类的属性或该属性的属性值。
1. Class.getDeclaredField(String name);
返回一个 Field 对象,该对象反映此 Class 对象所表示的类或接口的指定已声明字段(包括私有成员)。
2. Class.getDeclaredFields();
返回 Field 对象的一个数组,该数组包含此 Class 对象所表示的类或接口所声明的所有字段(包括私有成员)。
3. Class.getField(String name);
返回一个 Field 对象,它反映此 Class 对象所表示的类或接口的指定公共成员字段。
4. Class.getFields();
返回一个包含某些 Field 对象的数组,该数组包含此 Class 对象所表示的类或接口的所有可访问公共字段。
// 获取所有属性(包括私有) Field[] class1Fields = class1.getDeclaredFields(); // 获取一个属性(通过该属性的名) Field class1Field = class1.getDeclaredField("name");
Field class1Field = class1.getDeclaredField("name"); class1Field.setAccessible(true); // 向对象的这个Field属性设置新值value class1Field.set(stu, "李狗蛋"); System.out.println(class1Field.get(stu)); // 输出结果为 李狗蛋
getType(): 获取属性声明时类型对象(返回class对象)
getGenericType() : 返回属性声的Type类型
getName() : 获取属性声明时名字
getAnnotations() : 获得这个属性上所有的注释
getModifiers() : 获取属性的修饰
isEnumConstant() : 判断这个属性是否是枚举类
isSynthetic() : 判断这个属性是否是 复合类
get(Object obj) : 取得obj对象这个Field上的值
set(Object obj, Object value) : 向obj对象的这个Field设置新值value