java反射构建对象和方法的反射调用

简介: java反射构建对象和方法的反射调用Java反射技术应用广泛,其能够配置:类的全限定名,方法和参数,完成对象的初始化,设置是反射某些方法。可以增强java的可配置性。1.1 通过反射构建对象(无参数):  例如我们使用 ReflectServiceImpl 类讲解这个例子1 public class ReflectServiceImpl {2 public void sayHello(String name){3 System.out.println("hello"+name);4 }5 }我们通过反射的方法去构建它。

java反射构建对象和方法的反射调用
Java反射技术应用广泛,其能够配置:类的全限定名,方法和参数,完成对象的初始化,设置是反射某些方法。可以增强java的可配置性。

1.1 通过反射构建对象(无参数):

  例如我们使用 ReflectServiceImpl 类讲解这个例子

1 public class ReflectServiceImpl {
2 public void sayHello(String name){
3 System.out.println("hello"+name);
4 }
5 }
我们通过反射的方法去构建它。

复制代码
1 public ReflectServiceImpl getInstance(){
2 ReflectServiceImpl object=null;
3 try {
4 object=(ReflectServiceImpl)Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl").newInstance();
5 } catch (InstantiationException | IllegalAccessException | ClassNotFoundException e) {
6 e.printStackTrace();
7 }
8 return object;
9 }
复制代码
其中第4行:object=(ReflectServiceImpl)Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl").newInstance();

是给类加载器注册一个类ReflectServiceImpl的权限定名,之后通过newInstance方法初始化一个类对象。

1.2 通过反射构建对象(类的构造器中带有参数):

我们使用ReflectServiceImpl2这个类去理解:

复制代码
1 public class ReflectServiceImpl2 {
2 private String name;
3 public ReflectServiceImpl2(String name) {
4 this.name=name;
5 }
6 public void sayHello(String name){
7 System.out.println("hello"+name);
8 }
9 }
复制代码
此时 ReflectServiceImpl2的构造器带有参数 public ReflectServiceImpl2(String name){xxxx};

此时我们该如何利用反射生成对象呢?只需要在类加载器注册的使用getConstructor(参数)方法。其中参数是我们构造器中的参数的类型。代码如下:

复制代码
1 public ReflectServiceImpl2 getInstance(){
2 ReflectServiceImpl2 object=null;
3 try {
4 object=(ReflectServiceImpl2)Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl2")
5 .getConstructor(String.class).newInstance("张三");
6 } catch (InstantiationException | IllegalAccessException | ClassNotFoundException | InvocationTargetException |NoSuchMethodException e) {
7 e.printStackTrace();
8 }
9 return object;
10 }
复制代码
如4、5行所示:

  先通过forName加载到类的加载器。然后通过getConstructor方法,它的参数可以是多个,这里定义String.class,意为有且只有一个参数类型为String 的构建方法。通过这个方法可以对重名方法进行排除,此时再用newInstance方法生成对象,只是newInstance方法也多了一个参数“张三”而已。实际上就等于object=new ReflectServiceImpl2("张三").只是利用了反射来生成对象而已。

1.3 反射方法

  在使用反射方法之前需要先获取对象,得到了方法才能够去反射。

我们使用 ReflectServiceImpl 类为例。

ReflectServiceImpl 类代码:

1 public class ReflectServiceImpl {
2 public void sayHello(String name){
3 System.out.println("hello"+name);
4 }
5 }
调用方法:

复制代码
1 public Object reflect(){
2 ReflectServiceImpl object=null;
3 Object returnObj=null;
4 //反射生成对象
5 try {
6 object = (ReflectServiceImpl) Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl").newInstance();
7 //反射生成方法并调度
8 Method method = object.getClass().getMethod("sayHello", String.class);
9 returnObj= method.invoke(object, "张三");
10 }catch( ClassNotFoundException| NoSuchMethodException| InvocationTargetException| IllegalAccessException| InstantiationException e ) {
11 e.printStackTrace();
12 }
13 return returnObj;
14 }
复制代码
当有具体对象 object(类型为ReflectServiceImpl),而不知道具体是哪个类的时候,也可以使用object.getClass().getMethod("sayHello", String.class);来替代它,其中第一个参数是方法的名称,第二个参数是参数类型,是一个列表,多个参数可以继续编写多个类型,这样便能够获得反射的方法对象。反射方法时运用 method.invoke(object, "张三");调用的,第一个参数为object,就是确定用哪个对象调用方法,而“张三”是参数,这就等同于object.sayHello("张三");若存在多个参数可以写成Method.invoke(target,obj1,obj2.obj3...),这些要根据对象的具体方法来确定。

1.4 测试

以ReflectServiceImpl为例:

复制代码
1 package com.lean.reflect;
2 import java.lang.reflect.InvocationTargetException;
3 import java.lang.reflect.Method;
4 public class ReflectServiceImpl {
5 //属性
6 private String name;
7 //默认的构造方法
8 public ReflectServiceImpl() {
9 super();
10 }
11 //带参数的构造方法
12 public ReflectServiceImpl(String name) {
13 this.name=name;
14 }
15 //方法 sayHelo
16 public void sayHello(String name){
17 System.out.println("hello "+name);
18 }
19 //调用方法
20 public Object reflect(){
21 ReflectServiceImpl object=null;
22 Object returnObj=null;
23 //反射生成对象
24 try {
25 object = (ReflectServiceImpl) Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl").newInstance();
26 //反射生成方法并调度
27 Method method = object.getClass().getMethod("sayHello", String.class);
28 returnObj= method.invoke(object, "张三");
29 }catch( ClassNotFoundException| NoSuchMethodException| InvocationTargetException| IllegalAccessException| InstantiationException e ) {
30 e.printStackTrace();
31 }
32 return returnObj;
33 }
34 //获取对象
35 public ReflectServiceImpl getInstance(){
36 ReflectServiceImpl object=null;
37 try {
38 object=(ReflectServiceImpl)Class.forName("com.lean.ssm.chapter2.reflect.ReflectServiceImpl").newInstance();
39 } catch (InstantiationException | IllegalAccessException | ClassNotFoundException e) {
40 e.printStackTrace();
41 }
42 return object;
43 }
44 //测试
45 public static void main(String[] args) {
46 ReflectServiceImpl rsl= new ReflectServiceImpl();
47 rsl.reflect();
48 }
49 }
复制代码
效果图:

原文地址https://www.cnblogs.com/zyxsblogs/p/11225233.html

相关文章
|
6天前
|
Java 编译器
Java——类与对象(继承和多态)
本文介绍了面向对象编程中的继承概念,包括如何避免重复代码、构造方法的调用规则、成员变量的访问以及权限修饰符的使用。文中详细解释了继承与组合的区别,并探讨了多态的概念,包括向上转型、向下转型和方法的重写。此外,还讨论了静态绑定和动态绑定的区别,以及多态带来的优势和弊端。
20 9
Java——类与对象(继承和多态)
|
6天前
|
SQL Java 编译器
Java——类与对象(封装)
封装是面向对象编程中的概念,指将数据(属性)和相关操作(方法)组合成独立单元(类),使外部无法直接访问对象的内部状态,只能通过提供的方法进行交互,从而保护数据安全。例如,手机将各种组件封装起来,只暴露必要的接口供外部使用。实现封装时,使用`private`关键字修饰成员变量,并提供`get`和`set`方法进行访问和修改。此外,介绍了包的概念、导入包的方式及其注意事项,以及`static`关键字的使用,包括静态变量和方法的初始化与代码块的加载顺序。
18 10
Java——类与对象(封装)
|
6天前
|
Java C语言
Java——类与对象
这段内容介绍了Java中的类和对象、`this`关键字及构造方法的基本概念。类是对现实世界事物的抽象描述,包含属性和方法;对象是类的实例,通过`new`关键字创建。`this`关键字用于区分成员变量和局部变量,构造方法用于初始化对象。此外,还介绍了标准JavaBean的要求和生成方法。
18 9
Java——类与对象
|
6天前
|
安全 Java API
【Java面试题汇总】Java基础篇——String+集合+泛型+IO+异常+反射(2023版)
String常量池、String、StringBuffer、Stringbuilder有什么区别、List与Set的区别、ArrayList和LinkedList的区别、HashMap底层原理、ConcurrentHashMap、HashMap和Hashtable的区别、泛型擦除、ABA问题、IO多路复用、BIO、NIO、O、异常处理机制、反射
【Java面试题汇总】Java基础篇——String+集合+泛型+IO+异常+反射(2023版)
|
1天前
|
Java
Java实现:将带时区的时间字符串转换为LocalDateTime对象
通过上述方法,你可以将带时区的时间字符串准确地转换为 `LocalDateTime`对象,这对于处理不需要时区信息的日期和时间场景非常有用。
39 4
|
1天前
|
SQL Java 关系型数据库
在Java中,创建数据源对象
在Java中,创建数据源对象
8 1
|
7天前
|
存储 Java
Java编程中的对象序列化与反序列化
【9月更文挑战第12天】在Java的世界里,对象序列化与反序列化是数据持久化和网络传输的关键技术。本文将带你了解如何通过实现Serializable接口来标记一个类的对象可以被序列化,并探索ObjectOutputStream和ObjectInputStream类的使用,以实现对象的写入和读取。我们还将讨论序列化过程中可能遇到的问题及其解决方案,确保你能够高效、安全地处理对象序列化。
|
7天前
|
JavaScript 前端开发 Java
通过JUnit5访问Java静态、私有、保护变量和方法
在《通过Gtest访问C++静态、私有、保护变量和方法》一文中介绍了如何通过Gtest访问C++静态、私有、保护变量和方法,本文介绍如何通过Junit5访问Java静态、私有、保护变量和方法。
13 0
|
存储 SQL Java
Java反射读取注解信息
Java反射读取注解信息
63 0
|
JSON 安全 Java