【commons-beanutils专题】002- ConstructorUtils 专题
文章目录
一、准备
0、ConstructorUtils 主要作用
主要用于通过反射技术操作对象的构造方法:执行构造方法、获得指定构造方法等;
普通和精确的区别:普通的会找到兼容类型的方法,精确的只会匹配到确切的参数类型的方法。
1、引入 commons-beanutils 依赖
<!--引入依赖commons-beanutils-->
<dependency>
<groupId>commons-beanutils</groupId>
<artifactId>commons-beanutils</artifactId>
<version>1.9.4</version>
</dependency>
2、pom.xml 文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.7.1</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.zibo</groupId>
<artifactId>zibo2022</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>zibo2022</name>
<description>zibo2022</description>
<properties>
<java.version>17</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!--引入依赖commons-beanutils-->
<dependency>
<groupId>commons-beanutils</groupId>
<artifactId>commons-beanutils</artifactId>
<version>1.9.4</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.7.1</version>
<configuration>
<excludes>
<exclude>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</exclude>
</excludes>
</configuration>
</plugin>
</plugins>
</build>
</project>
3、实体类
package com.zibo.zibo2022.constructor_utils.entity;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author zibo
* @date 2022/7/13 0013 18:29
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class Student {
/**
* 名字
*/
private String name;
/**
* 年龄
*/
private Integer age;
/**
* 地址
*/
private String address;
/**
* 单参数构造方法
* @param name 名字
*/
public Student(String name) {
this.name = name;
}
/**
* 多参数构造方法
* @param name 名字
* @param age 年龄
*/
public Student(String name, Integer age) {
this.name = name;
this.age = age;
}
/**
* 单参数构造方法
* @param age 年龄
*/
public Student(Integer age) {
this.age = age;
}
}
二、执行构造方法
1、执行构造方法 - 单个参数 - 自动获取类型
// 1、执行构造方法 - 单个参数 - 自动获取类型
try {
Student student1 = ConstructorUtils.invokeConstructor(Student.class, "张三");
System.out.println(student1.getName()); // 张三
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
2、执行构造方法 - 多个参数 - 自动获取类型
// 2、执行构造方法 - 多个参数 - 自动获取类型
try {
// 参数列表
Object[] args1 = new Object[] {"李四", 18};
Student student2 = ConstructorUtils.invokeConstructor(Student.class, args1);
System.out.println(student2.getName()); // 李四
System.out.println(student2.getAge()); // 18
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
3、执行构造方法 - 多个参数 - 手动设置类型
// 3、执行构造方法 - 多个参数 - 手动设置类型
try {
// 参数列表
Object[] args1 = new Object[] {"王五", 20};
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Student student3 = ConstructorUtils.invokeConstructor(Student.class, args1, types);
System.out.println(student3.getName()); // 王五
System.out.println(student3.getAge()); // 20
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
三、执行精确的构造方法
1、执行精确的构造方法 - 单个参数 - 自动获取类型
// 4、执行精确的构造方法 - 单个参数 - 自动获取类型
try {
Student student4 = ConstructorUtils.invokeExactConstructor(Student.class, "张三");
System.out.println(student4.getName()); // 张三
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
2、执行精确的构造方法 - 多个参数 - 自动获取类型
// 5、执行精确的构造方法 - 多个参数 - 自动获取类型
try {
// 参数列表
Object[] args1 = new Object[] {"李四", 18};
Student student5 = ConstructorUtils.invokeExactConstructor(Student.class, args1);
System.out.println(student5.getName()); // 李四
System.out.println(student5.getAge()); // 18
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
3、执行精确的构造方法 - 多个参数 - 手动设置类型
// 6、执行精确的构造方法 - 多个参数 - 手动设置类型
try {
// 参数列表
Object[] args1 = new Object[] {"王五", 20};
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Student student6 = ConstructorUtils.invokeExactConstructor(Student.class, args1, types);
System.out.println(student6.getName()); // 王五
System.out.println(student6.getAge()); // 20
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
四、指定类型,获取构造方法
1、指定一个类型,获取单参构造方法(测试1)
// 7、指定一个类型,获取单参构造方法(测试1)
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, String.class);
Student student7 = constructor.newInstance("马六");
System.out.println(student7.getName()); // 马六
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
2、指定一个类型,获取单参构造方法(测试2)
// 8、指定一个类型,获取单参构造方法(测试2)
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, Integer.class);
Student student8 = constructor.newInstance(26);
System.out.println(student8.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
3、指定一个类型列表,获取多参构造方法
// 9、指定一个类型列表,获取多参构造方法
try {
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, types);
Student student9 = constructor.newInstance("马六", 26);
System.out.println(student9.getName()); // 马六
System.out.println(student9.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
五、获取给定构造函数的可访问版本
// 10、获取给定构造函数的可访问版本
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, Integer.class);
Constructor<Student> constructor1 = ConstructorUtils.getAccessibleConstructor(constructor);
Student student10 = constructor1.newInstance(26);
System.out.println(student10.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
六、完整代码
package com.zibo.zibo2022.constructor_utils.main;
import com.zibo.zibo2022.constructor_utils.entity.Student;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import org.apache.commons.beanutils.ConstructorUtils;
/**
* @author zibo
* @date 2022/7/13 0013 18:31
*/
public class Main {
public static void main(String[] args) {
// 1、执行构造方法 - 单个参数 - 自动获取类型
try {
Student student1 = ConstructorUtils.invokeConstructor(Student.class, "张三");
System.out.println(student1.getName()); // 张三
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 2、执行构造方法 - 多个参数 - 自动获取类型
try {
// 参数列表
Object[] args1 = new Object[] {"李四", 18};
Student student2 = ConstructorUtils.invokeConstructor(Student.class, args1);
System.out.println(student2.getName()); // 李四
System.out.println(student2.getAge()); // 18
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 3、执行构造方法 - 多个参数 - 手动设置类型
try {
// 参数列表
Object[] args1 = new Object[] {"王五", 20};
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Student student3 = ConstructorUtils.invokeConstructor(Student.class, args1, types);
System.out.println(student3.getName()); // 王五
System.out.println(student3.getAge()); // 20
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 4、执行精确的构造方法 - 单个参数 - 自动获取类型
try {
Student student4 = ConstructorUtils.invokeExactConstructor(Student.class, "张三");
System.out.println(student4.getName()); // 张三
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 5、执行精确的构造方法 - 多个参数 - 自动获取类型
try {
// 参数列表
Object[] args1 = new Object[] {"李四", 18};
Student student5 = ConstructorUtils.invokeExactConstructor(Student.class, args1);
System.out.println(student5.getName()); // 李四
System.out.println(student5.getAge()); // 18
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 6、执行精确的构造方法 - 多个参数 - 手动设置类型
try {
// 参数列表
Object[] args1 = new Object[] {"王五", 20};
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Student student6 = ConstructorUtils.invokeExactConstructor(Student.class, args1, types);
System.out.println(student6.getName()); // 王五
System.out.println(student6.getAge()); // 20
} catch (NoSuchMethodException | IllegalAccessException |
InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 7、指定一个类型,获取单参构造方法(测试1)
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, String.class);
Student student7 = constructor.newInstance("马六");
System.out.println(student7.getName()); // 马六
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 8、指定一个类型,获取单参构造方法(测试2)
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, Integer.class);
Student student8 = constructor.newInstance(26);
System.out.println(student8.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 9、指定一个类型列表,获取多参构造方法
try {
// 参数类型列表
Class<?>[] types = new Class[] {String.class, Integer.class};
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, types);
Student student9 = constructor.newInstance("马六", 26);
System.out.println(student9.getName()); // 马六
System.out.println(student9.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
// 10、获取给定构造函数的可访问版本
try {
Constructor<Student> constructor = ConstructorUtils.getAccessibleConstructor(Student.class, Integer.class);
Constructor<Student> constructor1 = ConstructorUtils.getAccessibleConstructor(constructor);
Student student10 = constructor1.newInstance(26);
System.out.println(student10.getAge()); // 26
} catch (IllegalAccessException | InvocationTargetException | InstantiationException e) {
throw new RuntimeException(e);
}
}
}