目录
利用反射获取成员变量
Class类中用于获取成员变量的方法
实例
获取成员变量的权限修饰符
获取成员变量的类型
获取成员变量名
Field类中用于创建对象的方法
利用反射获取成员变量
之前说 “万物皆对象” 在这里 我们把一个个 成员变量也封装成一个个Field 类对象
Class类中用于获取成员变量的方法
Field[]getFields() | 返回所有公共成员变量对象的数组 |
Field[]getDeclaredFields() | 返回所有成员变量对象的数组 |
Field getField(Stringname) | 返回单个公共成员变量对象 |
Field getDeclaredField(Stringname) | 返回单个成员变量对象 |
实例
- 获取全部的成员变量
打开 IDEA ,新建一个Student 类 有 name 和age ,gender 三个成员变量。并且成员变量之间的修饰符也有所不同
private String name; private int age; public String gender;要求通过反射 获取这些成员变量
注意;加了Declared 表示可以获得全部权限修饰符的 成员变量对象,如果不加,则表示 获得公共的权限修饰符修饰的成员变量对象
步骤
1 获得 目标类 的Class 类对象
2 调用Class类下的方法如:Field[]getDeclaredFields(),Field[]getFields()
try {Class<?> aClass = Class.forName("fs.exerise02.Student");Field[] declaredFields = aClass.getDeclaredFields();for (Field declaredField : declaredFields) {System.out.println(declaredField);}} catch (Exception e) {throw new RuntimeException(e);}
运行结果
获取指定的成员变量
步骤
1 获得 目标类 的Class 类对象
2 调用Class类下的方法如:Field getField(Stringname),Field getDeclaredField(Stringname)
注意;加了Declared 表示可以获得全部权限修饰符的 成员变量对象,如果不加,则表示 获得公共的权限修饰符修饰的成员变量对象
try {Class<?> aClass = Class.forName("fs.exerise02.Student");Field name = aClass.getDeclaredField("name");System.out.println(name );} catch (Exception e) {throw new RuntimeException(e);}
注意:getDeclaredField方法的参数是可变参数并且参数为成员变量名
运行结果
获取成员变量的权限修饰符
权限修饰符对应的数字
- 这里和上一篇博客 CSDN 获取构造方法的权限修饰符一样
int modifiers = name.getModifiers();System.out.println(modifiers);
运行结果
获取成员变量的类型
使用 getType() 方法获得 成员变量的基本数据类型或引用数据类型
Class<?> type = name.getType();System.out.println(type);
获取成员变量名
System.out.println(name.getName());
注意:即使你不写,直接打印成员变量对象,也是可以得到成员变量名的
如上图所示
运行结果
Field类中用于创建对象的方法
void set(Object obj, Object value) 赋值 Object get(Object obj) 获取值 注意:以上方法和我们 Java 中的get/set 方法 类似 是获取成员变量或为成员变量赋值
实例
- 修改成员变量记录的值
按照原本的模式 使用new 关键字 创建Student 对象
Student student=new Student("小明",12,"男");System.out.println(student);
现在我想要name 值 不再是 小明,而是小米 。按照之前的写法是要么是重写一遍构造方法,重新赋值。要么使用set方法 替代之前的值。但这需要重新编译一遍。如果我想要在运行时修改值,之前的代码不动。这时候应该想到应该使用反射 来做
Student student=new Student("小明",12,"男");System.out.println(student);System.out.println("-----------------------------");Field name = aClass.getDeclaredField("name");name.setAccessible(true);name.set(student,"小米");System.out.println(student);} catch (Exception e) {throw new RuntimeException(e);}
发现
1 使用 setAccessible(true) 方法的原因是在 Student 类中 name 成员变量不是 被public 公共的权限修饰符修饰,表示无法为 name 成员变量 赋值
如果不调用 setAccessible(true) 方法 ,会报如下错误
2 了解 set(Object obj,新的属性值) 方法的用法
运行结果
- 获得成员变量的值
name.setAccessible(true);System.out.println(name.get(student));
运行结果