为了能够动态获取对象构造方法的信息,首先需要通过下列方法之一创建一个 Constructor 类型的对象或者数组。

 getConstructors()getConstructor(Class<?>…parameterTypes)getDeclaredConstructors()getDeclaredConstructor(Class<?>...parameterTypes)

如果是访问指定的构造方法,需要根据该构造方法的入口参数的类型来访问。例如,访问一个入口参数类型依次为 int 和 String 类型的构造方法,下面的两种方式均可以实现。

objectClass.getDeclaredConstructor(int.class,String.class);objectClass.getDeclaredConstructor(new Class[]{int.class,String.class});

创建的每个 Constructor 对象表示一个构造方法,然后利用 Constructor 对象的方法操作构造方法。

Constructor类的常用方法

方法名称 说明
isVarArgs() 查看该构造方法是否允许带可变数量的参数,如果允许,返回 true,否则返回false
getParameterTypes() 按照声明顺序以 Class 数组的形式获取该构造方法各个参数的类型
getExceptionTypes() 以 Class 数组的形式获取该构造方法可能抛出的异常类型
newInstance(Object … initargs) 通过该构造方法利用指定参数创建一个该类型的对象,如果未设置参数则表示采用默认无参的构造方法
setAccessiable(boolean flag) 如果该构造方法的权限为 private,默认为不允许通过反射利用 netlnstance()方法创建对象。如果先执行该方法,并将入口参数设置为 true,则允许创建对象
getModifiers() 获得可以解析出该构造方法所采用修饰符的整数

通过 java.lang.reflect.Modifier 类可以解析出 getMocMers() 方法的返回值所表示的修饰符信息。在该类中提供了一系列用来解析的静态方法,既可以查看是否被指定的修饰符修饰,还可以字符串的形式获得所有修饰符。

Modifier类的常用方法

静态方法名称 说明
isStatic(int mod) 如果使用 static 修饰符修饰则返回 true,否则返回 false
isPublic(int mod) 如果使用 public 修饰符修饰则返回 true,否则返回 false
isProtected(int mod) 如果使用 protected 修饰符修饰则返回 true,否则返回 false
isPrivate(int mod) 如果使用 private 修饰符修饰则返回 true,否则返回 false
isFinal(int mod) 如果使用 final 修饰符修饰则返回 true,否则返回 false
toString(int mod) 以字符串形式返回所有修饰符

下列代码判断对象 con 所代表的构造方法是否被 public 修饰,以及以字符串形式获取该构造方法的所有修饰符。

int modifiers = con.getModifiers();    // 获取构造方法的修饰符整数
boolean isPublic = Modifier.isPublic(modifiers);    // 判断修饰符整数是否为public
string allModifiers = Modifier.toString(modifiers);

示例如何调用 Constructor 类的方法获取构造方法的信息。

1 . 首先创建一个 Book 类表示图书信息。在该类中声明一个 String 型变量表示图书名称,两个 int 型变量分别表示图书编号和价格,并提供 3 个构造方法。

Book 类的最终代码如下:

public class Book {String name; // 图书名称int id, price; // 图书编号和价格// 空的构造方法private Book() {}// 带两个参数的构造方法protected Book(String _name, int _id) {this.name = _name;this.id = _id;}// 带可变参数的构造方法public Book(String... strings) throws NumberFormatException {if (0 < strings.length)id = Integer.valueOf(strings[0]);if (1 < strings.length)price = Integer.valueOf(strings[1]);}// 输出图书信息public void print() {System.out.println("name=" + name);System.out.println("id=" + id);System.out.println("price=" + price);}
}

2 . 编写测试类 Test,在该类的 main() 方法中通过反射访问 Book 类中的所有构造方法,并将该构造方法是否带可变类型参数、入口参数类型和可能拋出的异常类型信息输出到控制台。

Test 类的代码如下:

public class Test {public static void main(String[] args) {// 获取动态类BookClass book = Book.class;// 获取Book类的所有构造方法Constructor[] declaredContructors = book.getDeclaredConstructors();// 遍历所有构造方法for (int i = 0; i < declaredContructors.length; i++) {Constructor con = declaredContructors[i];// 判断构造方法的参数是否可变System.out.println("查看是否允许带可变数量的参数:" + con.isVarArgs());System.out.println("该构造方法的入口参数类型依次为:");// 获取所有参数类型Class[] parameterTypes = con.getParameterTypes();for (int j = 0; j < parameterTypes.length; j++) {System.out.println(" " + parameterTypes[j]);}System.out.println("该构造方法可能拋出的异常类型为:");// 获取所有可能拋出的异常类型Class[] exceptionTypes = con.getExceptionTypes();for (int j = 0; j < exceptionTypes.length; j++) {System.out.println(" " + parameterTypes[j]);}// 创建一个未实例化的Book类实例Book book1 = null;while (book1 == null) {try { // 如果该成员变量的访问权限为private,则拋出异常if (i == 1) {// 通过执行带两个参数的构造方法实例化book1book1 = (Book) con.newInstance("Java 教程", 10);} else if (i == 2) {// 通过执行默认构造方法实例化book1book1 = (Book) con.newInstance();} else {// 通过执行可变数量参数的构造方法实例化book1Object[] parameters = new Object[] { new String[] { "100", "200" } };book1 = (Book) con.newInstance(parameters);}} catch (Exception e) {System.out.println("在创建对象时拋出异常,下面执行 setAccessible() 方法");con.setAccessible(true); // 设置允许访问 private 成员}}book1.print();System.out.println("=============================\n");}}
}

3 . 运行测试类 Test,当通过反射访问默认构造方法 Book() 时,将看到如下所示的输出。

查看是否允许带可变数量的参数:false
该构造方法的入口参数类型依次为:
该构造方法可能抛出的异常类型为:
在创建对象时抛出异常,下面执行setAccessible()方法
name = null
id = 0
price = 0
=============================

当通过反射访问两个参数的构造方法 Book(String_name,int_id) 时,将看到如下所示的输出。

查看是否允许带可变数量的参数:false
该构造方法的入口参数类型依次为:
class java.lang.String
int
该构造方法可能抛出的异常类型为:
在创建对象时抛出异常,下面执行setAccessible()方法
name = null
id = 0
price = 0
=============================

当通过反射访问可变参数数量的构造方法 Book(String…strings) 时,将看到如下所示的输出。

查看是否允许带可变数量的参数:true
该构造方法的入口参数类型依次为:
class java.lang.String;
该构造方法可能抛出的异常类型为:
class java.lang.String;
在创建对象时抛出异常,下面执行setAccessible()方法
name = null
id = 0
price = 0
=============================

Java通过反射访问构造方法相关推荐

  1. Java通过反射访问成员变量

    通过下列任意一个方法访问成员变量时将返回 Field 类型的对象或数组. getFields()getField(String name)getDeclaredFields()getDeclaredF ...

  2. [Java基础]反射获取构造方法并使用练习

    Student类代码如下: package ClassObjectPack;public class Student {private String name;int age;public Strin ...

  3. [Java基础]反射获取构造方法并使用

    代码如下: package ClassObjectPack;import java.lang.annotation.Annotation; import java.lang.reflect.Const ...

  4. JAVA创建一个私有域_使用java基础反射访问私有域、方法和构造函数

    1.类 public class ConfigData { private Map configs = null; private final String fileName = "conf ...

  5. java 反射 成员变量_java使用反射访问成员变量的值示例

    本文实例讲述了java使用反射访问成员变量的值.分享给大家供大家参考,具体如下: 一 代码 import java.lang.reflect.*; class Person { private Str ...

  6. Java反射获取构造方法

    [通过反射获取构造方法并使用] 获取构造方法 public Constructor[] getConstructors():所有公共构造方法 public Constructor[] getDecla ...

  7. sqlite字段是否存在_学习廖雪峰的JAVA教程---反射(访问字段)

    对任意的一个Object实例,只要我们获取了它的Class,就可以获取它的一切信息. 我们先看看如何通过Class实例获取字段信息.Class类提供了以下几个方法来获取字段: Field getFie ...

  8. java 反射 main_java – 通过反射访问main方法中的局部变量

    Since main is static, is it possible to access instanceOfB in order to access the value of _nonStati ...

  9. java反射访问室友属性_如何与家人,室友和客人共享HomeKit访问权限

    java反射访问室友属性 What's the point of having a house of the future if your family members, roommates, or ...

最新文章

  1. CoordinatorLayout 和 AppBarLayout 实现折叠效果 底部带阴影的处理方法
  2. android studio 的中文网站
  3. 树莓派配置路由_树莓派安装Ubuntu 20.04 LTS并配置
  4. Mxnet - Understanding weight shape for Dense Layer MXNET权重参数形状的疑惑(内部设计形式行列谁在前不用管,多个转置运算而已)
  5. 几种特征选择方法的比较,孰好孰坏?
  6. 网站如何接入微信支付功能?微信支付详细教程它来了(建议收藏)
  7. 垂直居中重要方法理解---重点是方法三
  8. 解决 IntelliJ IDEA 安装后界面消失,再次打开后界面不动
  9. qDebug格式化输出类型
  10. archives_do.php,织梦后台文章管理中增加批量添加tag标签功能
  11. Linux CGLIB升级,cglib升级建议
  12. 几个阿里,美团,腾讯大佬的公众号!超级变态!
  13. 765. 情侣牵手--(每日一难phase2--day14)
  14. 实用的图片批量压缩优化工具
  15. 2020年中国不支持苹果_苹果2020年9月事件提示
  16. HTML两张图片翻转,canvas实现图片镜像翻转的2种方式
  17. 基于FPGA的卷积神经网络加速器(绪论)
  18. 怎么把电脑上的文件备份到百度网盘?
  19. 推荐一款免费的数据库管理工具,比Navicat还要好用,功能还很强大!
  20. 信息安全意识-密码安全

热门文章

  1. 桔子浏览器电脑版收藏夹位置在哪里 收藏夹位置路径
  2. 钉钉项目任务怎么添加审批表单
  3. windows7电脑怎么永久关闭广告
  4. SAP ABAP 打印(smartforms方式)
  5. Java中switch参数传null会引起异常——Java 语法糖
  6. postman如何发送application/json类的post请求
  7. 解决MongoDB Compass
  8. mysql区间段_解决针对MySQL中对于某一个区间段范围的数据更新的情况
  9. 用计算机弹奏曲子童年,5.这首曲子使我想起了我的童年.十.书面表达现在.计算机游戏非常盛行.这是一件好事还是一件坏事?请你用英语写一篇短文来陈述自己的观点.并说明理由.字数:80-120....
  10. 计算机应用常用的30个函数,Excel中常用函数的使用