反射Reflect
介绍反射及作用
- 反射(Reflect)是在运行时动态访问类与对象的技术。
- 反射是JDK1.2版本后的高级特性,隶属于java.lang.reflect
- 大多数Java框架都基于反射实现参数配置,动态注入等特性
我个人理解就是在程序运行之后才去动态识别访问到具体类和对象消息的技术
讲解反射四个核心类
Class类
- Class是JVM中代表"类和接口"的类
- Class对象具体包含了某个特定类的结构信息
- 通过Class对象可以获取到对应类的构造方法/方法/成员变量
Class类的核心方法:
下面给出示例代码:
基类:
package com.imooc.reflect.entity;
public class Employee {
private Integer eno;
public String ename;
private Float salary;
private String dname;
public Employee(){
System.out.println("默认构造执行");
}
public Employee(Integer eno, String ename, Float salary, String dname) {
this.eno = eno;
this.ename = ename;
this.salary = salary;
this.dname = dname;
System.out.println("带参构造执行");
}
public Employee updateSalary(Float val){
this.setSalary(val+this.salary);
System.out.println(this.ename+"调薪至"+this.salary);
return this;
}
public Integer getEno() {
return eno;
}
public void setEno(Integer eno) {
this.eno = eno;
}
public String getEname() {
return ename;
}
public void setEname(String ename) {
this.ename = ename;
}
public Float getSalary() {
return salary;
}
public void setSalary(Float salary) {
this.salary = salary;
}
public String getDname() {
return dname;
}
public void setDname(String dname) {
this.dname = dname;
}
static {
System.out.println("Employee 类已被初始化");
}
@Override
public String toString() {
return "Employee{" +
"eno=" + eno +
", ename='" + ename + '\'' +
", salary=" + salary +
", dname='" + dname + '\'' +
'}';
}
}
Class测试类:
package com.imooc.reflect;
import com.imooc.reflect.entity.Employee;
public class ClassSample {
public static void main(String[] args) {
try {
System.out.println("Employee等待被加载到JVM中");
Class employeeClass = Class.forName("com.imooc.reflect.entity.Employee");
System.out.println("Employee已经被加载到JVM中");
Employee employee = (Employee) employeeClass.newInstance();
System.out.println(employee);
} catch (ClassNotFoundException e) {
throw new RuntimeException(e);
} catch (InstantiationException e) {
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
}
}
}
Constructor构造方法类
Costructor是Java类中的构造方法的抽象
Constructor对象包含了具体类的某个具体构造方法的声明
通过Constructor对象调用带参构造方法创建对象
Constructor类核心方法
Constructor测试类
package com.imooc.reflect;
import com.imooc.reflect.entity.Employee;
import java.lang.reflect.Constructor;
public class ConstructorSample {
public static void main(String[] args) {
try {
Class employeeClass = Class.forName("com.imooc.reflect.entity.Employee");
Constructor constructor = employeeClass.getConstructor(new Class[]{
Integer.class, String.class, Float.class, String.class
});
Employee employee = (Employee) constructor.newInstance(new Object[]{
1001, "王炜", 10000f, "研发部"
});
System.out.println(employee);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
Method方法类
- Method对象指代某个类的方法的描述
- Method对象使用classObj.getMethod()方法获取
- 通过Method对象掉用指定对象的对应方法
Method类核心方法
Method测试类:
package com.imooc.reflect;
import com.imooc.reflect.entity.Employee;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
public class MethodSample {
public static void main(String[] args) throws NoSuchMethodException {
Employee employe;
Class employeeClass;
try {
employeeClass = Class.forName("com.imooc.reflect.entity.Employee");
Constructor constructor = employeeClass.getConstructor(new Class[]{
Integer.class, String.class, Float.class, String.class
});
employe = (Employee) constructor.newInstance(new Object[]{
1002, "王炜", 18000f, "研发部"
});
} catch (ClassNotFoundException | NoSuchMethodException e) {
throw new RuntimeException(e);
} catch (InvocationTargetException e) {
throw new RuntimeException(e);
} catch (InstantiationException e) {
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
}
Method updateSalaryMethod = employeeClass.getMethod("updateSalary", Float.class);
try {
Employee employee = (Employee) updateSalaryMethod.invoke(employe,new Object[] {
2000f
});
System.out.println(employe);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
} catch (InvocationTargetException e) {
throw new RuntimeException(e);
}
}
}
Field成员变量类
- Field对应某个具体类中的成员变量的声明
- Field对象使用classObj.getField()方法获取
- 通过Field对象可作为某对象成员变量赋值/取值
Field类核心方法
Field测试类
package com.imooc.reflect;
import com.imooc.reflect.entity.Employee;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
public class FieldSample {
public static void main(String[] args) throws InvocationTargetException, InstantiationException, IllegalAccessException, NoSuchFieldException, ClassNotFoundException, NoSuchMethodException {
Class employeeClass= Class.forName("com.imooc.reflect.entity.Employee");
Constructor constructor = employeeClass.getConstructor(new Class[]{
Integer.class, String.class, Float.class, String.class
});
Employee employee = (Employee) constructor.newInstance(new Object[] {
1000,"王炜",18000f,"研发部"
});
Field field = employeeClass.getField("ename");
String ename = (String) field.get(employee);
System.out.println("ename="+ename);
field.set(employee,"张龙珠");
ename = (String) field.get(employee);
System.out.println("ename="+ename);
}
}
getDeclared系列方法
- getDeclaredConstructor(s)|Method(s)|Field(s)获取对应对象
- getConstructorConstructor(s)|Method(s)|Field(s)只能获取到public对象
- 访问非作用域内构造方法,方法,成员变量,会抛出异常
测试类:
package com.imooc.reflect;
import com.imooc.reflect.entity.Employee;
import com.sun.javaws.IconUtil;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.List;
public class getDeclaredSample {
public static void main(String[] args) {
try {
Class employeeClass = Class.forName("com.imooc.reflect.entity.Employee");
Constructor constructor = employeeClass.getConstructor(new Class[]{
Integer.class, String.class, Float.class, String.class
});
Employee employee = (Employee) constructor.newInstance(new Object[]{
1001, "王炜", 10000f, "研发部"
});
Field[] list = employeeClass.getDeclaredFields();
for (int i = 0; i < list.length; i++) {
// System.out.println(list[i].getName());
// 判断类型
if (list[i].getModifiers() == 1) {
// PUBLIC 修饰
Object val = list[i].get(employee);
System.out.println(list[i].getName() + ".value = " + val);
} else if (list[i].getModifiers() == 2) {
//private 修饰
String methodName = "get" + list[i].getName().substring(0, 1).toUpperCase() + list[i].getName().substring(1);
Method method = employeeClass.getMethod(methodName);
Object val = method.invoke(employee);
System.out.println(list[i].getName() + ".value = " + val);
}
}
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}