java反射
Java 反射机制是在运行状态中,对于任意一个类,都能够获得这个类的所有属性和方法,对于任意一个对象都能够调用它的任意一个属性和方法。这种在运行时动态的获取信息以及动态调用对象的方法的功能称为 Java 的反射机制。
实体类
package com.lzc.reflect;
public class Person {
public Integer id;
String avatar;
protected String sex;
private String name;
private Integer age;
// 无参构造方法
public Person() {
System.out.println("【公有】无参构造方法");
}
// 一个参数的构造方法
public Person(String name) {
this.name = name;
System.out.println("【公有】一个参数的构造方法:name=" + name);
}
// 两个参数的构造方法
public Person(String name, Integer age) {
this.name = name;
this.age = age;
System.out.println("【公有】两个参数的构造方法:name=" + name + ",age=" + age);
}
// 私有的构造方法
private Person(Integer age) {
this.age = age;
System.out.println("【私有】构造方法:age=" + age);
}
public void methed1(String name) {
System.out.println("公有方法:name = " + name);
}
void methed2() {
System.out.println("默认方法");
}
private void methed3(Integer age) {
System.out.println("私有方法:age = " + age);
}
protected void methed4() {
System.out.println("受保护方法");
}
@Override
public String toString() {
return "Person{" +
"id=" + id +
", avatar='" + avatar + '\'' +
", sex='" + sex + '\'' +
", name='" + name + '\'' +
", age=" + age +
'}';
}
}
获取Class对象
public class App
{
public static void main( String[] args ) throws ClassNotFoundException {
// 方法一
Person person = new Person();
Class cls1 = person.getClass();
// 方法二
Class cls2 = Person.class;
// 方法三
Class cls3 = Class.forName("com.lzc.reflect.Person"); // 通过包的路径获取
// 在运行期间一个类只有一个Class对象
System.out.println(cls1 == cls2); // true
System.out.println(cls1 == cls3); // true
}
}
通过反射获取类的构造方法
public class ConstructorsTest {
public static void main(String[] args) throws Exception {
// 加载class对象
Class clazz = Class.forName("com.lzc.reflect.Person");
System.out.println("--------所有公有构造方法--------");
Constructor[] cons = clazz.getConstructors();
for(Constructor c : cons){
System.out.println(c);
}
System.out.println("\n");
System.out.println("--------所有的构造方法(包括:私有、受保护、默认、公有)--------");
cons = clazz.getDeclaredConstructors();
for(Constructor c : cons){
System.out.println(c);
}
System.out.println("\n");
System.out.println("--------调用单个无参构造方法--------");
Constructor con = clazz.getConstructor(); // 获取单个公有的构造方法
Object obj = con.newInstance();
System.out.println("\n");
System.out.println("--------调用单个公有构造方法--------");
Constructor con1 = clazz.getConstructor(String.class, Integer.class); // 获取单个公有的构造方法
Object obj1 = con1.newInstance("lzc",22);
System.out.println("\n");
System.out.println("--------调用私有的、受保护的、共有的、默认的构造方法--------");
Constructor con2 = clazz.getDeclaredConstructor(Integer.class); // 获取单个私有的、受保护的、共有的、默认的构造方法
con2.setAccessible(true);// 如果是调用私有的就需要设置此权限,否则无法调用
Object obj2 = con2.newInstance(22);
System.out.println("\n");
}
}
通过反射获取类的字段
/**
* 获取所有共有的字段:public Field[] getFields()
* 获取所有的字段(包括私有、受保护、默认的):public Field[] getDeclaredFields()
* 获取公有字段:public Field getField(String name)
* 获取私有字段:public Field getDeclaredField(String name)
*/
public class FieldsTest {
public static void main(String[] args) throws Exception {
// 加载class对象
Class clazz = Class.forName("com.lzc.reflect.Person");
System.out.println("--------获取所有公有的字段--------");
Field[] fs = clazz.getFields();
for (Field f : fs) {
System.out.println(f);
}
System.out.println("\n");
System.out.println("--------获取所有的字段(包括私有、受保护、默认的)--------");
fs = clazz.getDeclaredFields();
for (Field f : fs) {
System.out.println(f);
}
System.out.println("\n");
System.out.println("--------获取公有字段并设置值--------");
Field field1 = clazz.getField("id");
// 获取一个对象,clazz.getConstructor()获取一个无参的构造函数
Object obj1 = clazz.getConstructor().newInstance();
field1.set(obj1,123456);
Person p1 = (Person)obj1;
System.out.println(p1.toString());
System.out.println("\n");
System.out.println("--------获取私有字段并设置值--------");
Field field2 = clazz.getDeclaredField("name");
field2.setAccessible(true); // 解除私有限定
Object obj2 = clazz.getConstructor().newInstance();
field2.set(obj2, "lizhencheng");
Person p2 = (Person)obj2;
System.out.println(p2.toString());
System.out.println("\n");
}
}
通过反射获取类的方法
public class MethodsTest {
public static void main(String[] args) throws Exception {
// 加载Class对象
Class clazz = Class.forName("com.lzc.reflect.Person");
System.out.println("-------- 获取所有公有方法(包括父类的) --------");
// 获取所有公有方法,
Method[] methods = clazz.getMethods();
for (Method m : methods) {
System.out.println(m.toString());
}
System.out.print("\n");
System.out.println("-------- 获取所有方法(默认的,共有的,私有的,受保护的),不包括继承的 --------");
// 获取所有的成员方法,包括私有的,
methods = clazz.getDeclaredMethods();
for (Method m : methods) {
System.out.println(m.toString());
}
System.out.print("\n");
System.out.println("-------- 获取一个公有的方法 --------");
Method method1 = clazz.getMethod("methed1", String.class);
// 获取一个对象
Object obj = clazz.getConstructor().newInstance();
method1.invoke(obj, "lzc");
System.out.print("\n");
System.out.println("-------- 获取一个私有的方法 --------");
Method method2 = clazz.getDeclaredMethod("methed3", Integer.class);
method2.setAccessible(true); // 解除私有限制
method2.invoke(obj, 22);
System.out.print("\n");
System.out.println("-------- 获取一个默认的无参方法 --------");
Method method3 = clazz.getDeclaredMethod("methed2",null);
method3.invoke(obj,null);
System.out.print("\n");
}
}