1. 基本概念
- 通常来说, 反射机制就是用于动态创建对象并且动态调用方法的, 在运行阶段来动态编程
2. Class类
2.1 基本概念
2.2 获取Class类的实例
package com.lagou.task20;
/**
* @author 西风月
* @date 2020/8/30
* @description
*/
public class ClassTest {
public static void main(String[] args) throws ClassNotFoundException {
//1. 使用数据类型.class的方式可以获取对应类型的Class实例
Class c1 = String.class;
System.out.println("c1 = " + c1); //自动调用 toString方法 class java.lang.String
c1 = int.class;
System.out.println("c1 = " + c1); //int
c1 = void.class;
System.out.println("c1 = " + c1); //void
System.out.println("===================================");
//2. 使用对象.getClass()的方式获取对应的Class对象
String str1 = new String("hello");
c1 = str1.getClass();
System.out.println("c1 = " + c1);
Integer i1 = 19;
c1 = i1.getClass();
System.out.println("c1 = " + c1);
int num = 5;
//num.getClass(); 基本数据类型的变量不能调用方法,方法属于引用或对象中
System.out.println("==========================");
//3. 使用包装类.TYPE的方法获取对应的基本数据类型的Class对象
c1 = Integer.TYPE;
System.out.println("c1 = " + c1);
c1 = Integer.class;
System.out.println("c1 = " + c1);
System.out.println("========================");
//4. 调用Class类中的forName方法来获取对应的Class对象
//c1 = Class.forName("String"); ClassNotFoundException 需要完整名称
c1 = Class.forName("java.lang.String");
System.out.println("c1 = " + c1);
c1 = Class.forName("java.util.Date");
System.out.println("c1 = " + c1);
//c1 = Class.forName("int");
//System.out.println("c1 = " + c1); ClassNotFoundException 基本数据类型不支持
System.out.println("===============================");
//5. 使用类加载器的方式来获取Class对象
ClassLoader classLoader = ClassTest.class.getClassLoader();
System.out.println("ClassLoader = " + classLoader);
c1 = classLoader.loadClass("java.lang.String"); //NullPointerException
System.out.println("c1 = " + c1);
}
}
2.3 常用的方法
package com.lagou.task20;
import java.io.*;
import java.util.Scanner;
/**
* @author 西风月
* @date 2020/8/30
* @description
*/
public class PersonConstructorTest {
public static void main(String[] args) throws IllegalAccessException, InstantiationException, ClassNotFoundException, IOException {
//1. 使用原始方式以无参形式构造Person类型的对象并打印
Person p1 = new Person();
System.out.println("无参方式创建的对象是:" + p1);
System.out.println("=======================");
//2. 使用反射机制创建Person类型对象
//2.1 创建对象的类型从输入获取
//Person person = Person.class.newInstance();
System.out.println("请输入要创建对象的类型:");
Scanner sc = new Scanner(System.in);
String str1 = sc.next();
//Class c1 = Class.forName("com.lagou.task20.Person");
Class c1 = Class.forName(str1);
System.out.println("无参方式创建的对象是:" + c1.newInstance());
//2.2 创建对象的类型从配置文件中读取
BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream("f:/a.txt")));
String str =null;
while((str = br.readLine()) != null) {
c1 = Class.forName(str);
System.out.println("无参方式创建的对象:" + c1.newInstance());
}
br.close();
}
}
3. Constructor类
3.1 基本的概念
3.2 Class类的常用方法
3.3 Contructor类的常用的方法
package com.lagou.task20;
import java.io.*;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.Scanner;
/**
* @author 西风月
* @date 2020/8/30
* @description
*/
public class PersonConstructorTest {
public static void main(String[] args) throws Exception {
//1. 使用原始方式以无参形式构造Person类型的对象并打印
Person p1 = new Person();
System.out.println("无参方式创建的对象是:" + p1);
System.out.println("=======================");
//2. 使用反射机制创建Person类型对象
//2.1 创建对象的类型从输入获取
//Person person = Person.class.newInstance();
System.out.println("请输入要创建对象的类型:");
Scanner sc = new Scanner(System.in);
String str1 = sc.next();
//Class c1 = Class.forName("com.lagou.task20.Person");
Class c1 = Class.forName(str1);
System.out.println("无参方式创建的对象是:" + c1.newInstance());
//2.2 创建对象的类型从配置文件中读取
BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream("f:/a.txt")));
String str =null;
while((str = br.readLine()) != null) {
c1 = Class.forName(str);
System.out.println("无参方式创建的对象:" + c1.newInstance());
}
br.close();
//获取Class对象对应类中的无参构造方法
c1 = Class.forName("com.lagou.task20.Person");
Constructor constructor = c1.getConstructor(String.class, int.class);
//使用获取无参构造方法构造对应的对象
//newInstance的形式参数是给Class对象的构造方法初始化
System.out.println("无参方式创建的对象是:" + constructor.newInstance("张三", 60));
Constructor[] constructors = c1.getConstructors();
for(Constructor ct : constructors) {
System.out.println("构造方法的修饰: " + ct.getModifiers());
System.out.println("构造方法的名称:" + ct.getName());
Class[] parameterTypes = ct.getParameterTypes();
System.out.print("构造方法的参数: ");
for(Class cs : parameterTypes) {
System.out.print(cs + " ");
}
System.out.println();
}
}
}
4 Field类
4.1 基本概念
4.2 Class类的常用方法
4.3 Field类的常用方法
package com.lagou.task20;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
/**
* @author 西风月
* @date 2020/8/30
* @description
*/
public class PersonFiledTest {
public static void main(String[] args) throws Exception {
//1. 使用原始方式获取对象并打印数值
//Person p1 = new Person("张飞", 30);
//System.out.println(p1.name);
// 使用反射机制获取对象的成员变量数值并打印
Class c1 = Class.forName("com.lagou.task20.Person");
Constructor constructor = c1.getConstructor(String.class, int.class);
Object o = constructor.newInstance("张飞", 30);
//设置java语言访问检查的取消
//Field field = c1.getField("name");
Field field = c1.getDeclaredField("name");
field.setAccessible(true);
//获取对象Object中名字为name的成员变量的数值
System.out.println("使用反射机制获取到的数值为:" + field.get(o));
//3. 使用原始方式来修改成员变量数值
//p1.name = "刘备";
//p1.age = 35;
//System.out.println(p1.name);
//4. 使用反射机制修改成员变量的数值
field.set(o, "关羽");
System.out.println(field.get(o));
//5. 获取Class对象对应类中所有的成员变量
Field[] declaredFields = c1.getDeclaredFields();
for(Field field1 : declaredFields) {
System.out.println(field1.getModifiers());
System.out.println(field1.getType());
System.out.println(field1.getName());
}
}
}
5. Method类
5.1 基本概念
5.2 Class类的常用方法
5.3 Method类的常用方法
package com.lagou.task20;
import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
public class PersonMethodTest {
public static void main(String[] args) throws Exception {
//使用反射机制构造对象并调用方法打印结果
//(1) 获取Class对象
Class c1 = Class.forName("com.lagou.task20.Person");
// (2) 根据Class对象来获取对应的构造方法
Constructor constructor = c1.getConstructor(String.class, int.class);
// (3) 构造对象
Object object = constructor.newInstance("zhangsan", 29);
// (4) 根据Class对象来获取对应的成员方法
Method getName = c1.getMethod("getName");
System.out.println("调用方法的返回值是:" + getName.invoke(object));
}
}
6. 获取其他结构信息