Java反射机制详解与使用方法大全!!!

❤ 作者主页:李奕赫揍小邰的博客
❀ 个人介绍:大家好,我是李奕赫!( ̄▽ ̄)~*
🍊 记得点赞、收藏、评论⭐️⭐️⭐️
📣 认真学习!!!🎉🎉

文章目录

  • Java反射机制简述
  • 1、四种方式获取Class类的对象
  • 2、获取class类对象的属性,构造和方法
  • 3、使用newInstance创建对象
  • 4、通过Constructor对象调用无参和有参方法
  • 5、使用反射动态调用有无参有无返回值的Method方法
  • 6、反射会破坏OOP对象
  • 7、方法重载
  • 8、setAccessible的作用

Java反射机制简述

  Java反射机制的核心时在程序运行时动态加载类并获取类的详细信息,从而可以调用类或对象的属性和方法。
  它的本质是JVM得到class对象之后,再通过class对象进行反编译,从而获取对象和类的各种信息。通过反射,可以在运行时动态地创建对象并调用其属性,不需要提前在编译期知道运行的对象是谁。

 

1、四种方式获取Class类的对象

  
前置:新建一个UserInfo实体类在com.jjl.domain下面
在这里插入图片描述

Class class1= UserInfo.class;
Class class2=new UserInfo().getClass();
Class class3=UserInfo.class.getClassLoader().loadClass("com.jjl.domain.UserInfo");
Class class4=Class.forName("com.jjl.domain.UserInfo");

 

2、获取class类对象的属性,构造和方法

  

public static void main(String[] args) {    
Class userInfoClass= UserInfo.class;    //属性列表    
Field[] a=userInfoClass.getDeclaredFields();      
//getFields()方法获取类的全部公共字段,getDeclaredFields()方法获取全部字段    
for(Field field:a){        
	System.out.println(field.getName());    
}    
//构造列表    
Constructor[] b=userInfoClass.getConstructors();    
for(Constructor constructor:b){        
	System.out.println(constructor.getName());    
}    
//方法列表    
Method[] c=userInfoClass.getDeclaredMethods();    
for(Method method:c){        
	System.out.println(method.getName());    
}}

 

3、使用newInstance创建对象

  

//不用new来创建对象,原理就是反射技术
String newObjectName="com.jjl.domain.UserInfo";
Class class4=Class.forName(newObjectName);
//newInstance开始创建对象
UserInfo userInfo=(UserInfo) class4.newInstance();

 

4、通过Constructor对象调用无参和有参方法

  

String newObjectName="com.jjl.domain.UserInfo";
Class class4=Class.forName(newObjectName);
Constructor constructor1=class4.getDeclaredConstructor();     //调用无参方法
UserInfo userInfo1=(UserInfo) constructor1.newInstance();
System.out.println(userInfo1.hashCode());
Constructor constructor=class4.getDeclaredConstructor(long.class,String.class,String.class);  //调用有参方法
System.out.println(constructor.newInstance(11,"a1","aa1").hashCode());
System.out.println(constructor.newInstance(12,"a2","aa2").hashCode());    //结果下图

 

5、使用反射动态调用有无参有无返回值的Method方法

String newObjectName="com.jjl.domain.UserInfo";
Class class4=Class.forName(newObjectName);
UserInfo userInfo=(UserInfo) class4.newInstance();
String methodName="test";
//调用无参无返回值的Method方法
Method method=class4.getDeclaredMethod(methodName);
System.out.println(method.getName());
method.invoke(userInfo);     //根据获取的方法,反射执行该方法  getName()获取名称,invoke()反射执行
//调用有参无返回值的Method方法
Method method=class4.getDeclaredMethod(methodName,String.class);
System.out.println(method.getName());
method.invoke(userInfo,"我的地址在北京");
//调用有参有返回值的Method方法
Method method=class4.getDeclaredMethod(methodName,Integer.class);
System.out.println(method.getName());
Object returnValue=method.invoke(userInfo,99999);
System.out.println("returnValue"+returnValue);

 

6、反射会破坏OOP对象

  单例模式由于构造方式式private的,不能new实例化对象,只有调用getOneInstance()获取自身对象,而且可以保证单例。但是使用反射技术能破坏OOP对象,导致可以创建出多个单例对象。

OneInstance o1=OneInstance.getOneInstance();    //单例模式(饱汉式) 保证当前进程只有一个实例对象
OneInstance o2=OneInstance.getOneInstance();
OneInstance o3=OneInstance.getOneInstance();
System.out.println(o1);
System.out.println(o2);
System.out.println(o3);
Class classRef=Class.forName("com.jjl.objectfactory.OneInstance");   //从这里开始使用反射实例化对象
Constructor c=classRef.getDeclaredConstructor();
c.setAccessible(true);
OneInstance one1=(OneInstance) c.newInstance();
OneInstance one2=(OneInstance) c.newInstance();
System.out.println(one1);
System.out.println(one2);

执行结果:
在这里插入图片描述

 

7、方法重载

  使用反射可以调用重载方法

public static void main(String[] args) throws IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException {
    Class class15=Test15.class;
    Object object=class15.newInstance();
    Method method1=class15.getDeclaredMethod("testMethod", String.class);
    Method method2=class15.getDeclaredMethod("testMethod", String.class,String.class);
    method1.invoke(object,"法国");
    method2.invoke(object,"中国","中国人");
}
public void testMethod(String username){
    System.out.println("public void testMethod(String username)");
    System.out.println(username);
}
public void testMethod(String username,String password){
    System.out.println("public void testMethod(String username,String password)");
    System.out.println(username+" "+password);
}

 

8、setAccessible的作用

  setAccessible功能是启用或禁用安全检查;具体的用处主要有两处,作用于方法上,method.setAccessible(true);作用于属性上field.setAccessible(true);
  将此对象的 accessible 标志设置为指示的布尔值。值为 true 则指示反射的对象在使用时应该取消 Java 语言访问检查。值为 false 则指示反射的对象应该实施 Java 语言访问检查;实际上setAccessible是启用和禁用访问安全检查的开关,并不是为true就能访问为false就不能访问 ;
  由于JDK的安全检查耗时较多.所以通过setAccessible(true)的方式关闭安全检查就可以达到提升反射速度的目的
 


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/67342.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

c++中的继承

文章目录 1.继承的概念及定义1.1继承的概念1.2继承的定义1.2.1定义格式1.2.2继承关系和访问限定符1.2.3继承基类成员访问方式的变化 2.基类和派生类对象赋值转换3.继承中的作用域4.派生类的默认成员函数5.继承与友元6.继承与静态成员7.复杂的菱形继承及菱形虚拟继承 1.继承的概…

【深度学习注意力机制系列】—— SKNet注意力机制(附pytorch实现)

SKNet(Selective Kernel Network)是一种用于图像分类和目标检测任务的深度神经网络架构,其核心创新是引入了选择性的多尺度卷积核(Selective Kernel)以及一种新颖的注意力机制,从而在不增加网络复杂性的情况…

opencv基础53-图像轮廓06-判断像素点与轮廓的关系(轮廓内,轮廓上,轮廓外)cv2.pointPolygonTest()

点到轮廓的距离 在 OpenCV 中,函数 cv2.pointPolygonTest()被用来计算点到多边形(轮廓)的最短距离(也 就是垂线距离),这个计算过程又称点和多边形的关系测试。该函数的语法格式为: retval cv2…

Linux —— 基础I/O

一,背景介绍 狭义的文件存放在磁盘上,广义上在Linux下一切皆文件;磁盘上的文件一般为永久存储的外设,本质上对文件的操作,即为对外设的输入和输出(简称I/O);空文件并不是不占磁盘文件…

uC-OS2 V2.93 STM32L476 移植:串口打印篇

前言 前几篇已经 通过 STM32CubeMX 搭建了 NUCLEO-L476RG 的 STM32L476RG 的 裸机工程,下载了 uC-OS2 V2.93 的源码,并把 uC-OS2 的源文件加入 Keil MDK5 工程,通过适配 Systick 系统定时器与 PendSV 实现任务调度,初步让 uC-OS2 …

Facebook商城号最全解析,Facebook Marketplace运营技巧

相信许多做跨境的小伙伴都听说过Facebook商城号。其实所谓的商城并不是Facebook Shop,而是指Facebook Marketplace,它不像前者需要各类入驻条件,只要拥有facebook账号而且所在地区有能够使用marketplace就可以在上面进行商品售卖。这种低成本…

validator入门

validator中文文档地址和英文地址 https://docs.jboss.org/hibernate/validator/4.2/reference/zh-CN/html/validator-gettingstarted.html https://docs.jboss.org/hibernate/validator/6.0/reference/en-US/html_single/#preface自定义hibernate-validator校验 工具类Valid…

设计模式(4)装饰模式

一、介绍: 1、应用场景:把所需的功能按正确的顺序串联起来进行控制。动态地给一个对象添加一些额外的职责,就增加功能来说,装饰模式比生成子类更加灵活。 当需要给一个现有类添加附加职责,而又不能采用生成子类的方法…

谷歌关闭跨域限制.(生成一个开发浏览器),Chrome关闭跨域

(一)、首先找到浏览器在电脑磁盘中的位置,并复制 (二)、复制一个浏览器的快捷方式到桌面(不影响正常浏览器) (三)、chrom鼠标右键属性,修改快捷方式的目标 (四)chrome.exe 后面添加 --disable-web-security --user-data-dir 复制的Chrome浏览…

力扣hot100刷题记录

二刷hot100&#xff0c;坚持每天打卡&#xff01;&#xff01;&#xff01;Today&#xff1a;2023-8-10 1. 两数之和 // 先求差&#xff0c;再查哈希表 public int[] twoSum(int[] nums, int target) {Map<Integer,Integer> map new HashMap<>();for(int i 0;i&…

窥探系列之Mybatis-plus XML分页查询

mybatisPlus分页查总数 Page类在mybatisPlus中用于分页查询&#xff0c;继承Pagination类&#xff0c;Pagination类的searchCount字段控制是否查询总记录数 顺着看哪里用到了searchCount&#xff1a; com.baomidou.mybatisplus.plugins.PaginationInterceptor 是mybatisPlus…

安防监控视频汇聚EasyCVR平台的FLV视频流在VLC中无法播放的原因排查

众所周知&#xff0c;TSINGSEE青犀视频汇聚平台EasyCVR可支持多协议方式接入&#xff0c;包括主流标准协议国标GB28181、RTSP/Onvif、RTMP等&#xff0c;以及厂家私有协议与SDK接入&#xff0c;包括海康Ehome、海大宇等设备的SDK等。在视频流的处理与分发上&#xff0c;视频监控…

PyTorch 微调终极指南:第 2 部分 — 提高模型准确性

一、说明 如今&#xff0c;在训练深度学习模型时&#xff0c;通过在自己的数据上微调预训练模型来迁移学习已成为首选方法。通过微调这些模型&#xff0c;我们可以利用他们的专业知识并使其适应我们的特定任务&#xff0c;从而节省宝贵的时间和计算资源。本文分为四个部分&…

如何使用 AT+WEBSERVER 指令实现自定义的 Webserver html 网页配网

开启 AT 固件中的 Webserver 指令和 FS 指令支持 乐鑫官网发布的默认通用 AT 固件不支持 webserver 配网功能&#xff0c; 需要用户自己搭建 esp-at 环境&#xff0c;并在 sdkconfig 中开启 webserver AT 指令 和 FS 指令的支持&#xff0c; 如下图所示&#xff1a; 测试 AT 固…

Elasticsearch 与 OpenSearch:揭开性能差距

作者&#xff1a;George Kobar, Ugo Sangiorgi 对于任何依赖快速、准确搜索数据的组织来说&#xff0c;强大、快速且高效的搜索引擎是至关重要的元素。 对于开发人员和架构师来说&#xff0c;选择正确的搜索平台可以极大地影响你的组织提供快速且相关结果的能力。 在我们全面的…

oracle积累增量和差异增量

积累增量和差异增量&#xff1a; 对于 RMAN 来说&#xff0c;积累增量备份和差异增量备份都是增量备份的一种形式&#xff0c;它们之间的区别在于备份的范围和备份集的方式。 积累增量备份&#xff1a;在进行积累增量备份时&#xff0c;RMAN 会备份自最后一次完全备份或增量备…

FPGA外部触发信号毛刺产生及滤波

1、背景 最近在某个项目中&#xff0c;遇到输入给FPGA管脚的外部触发信号因为有毛刺产生&#xff0c;导致FPGA接收到的外部触发信号数量多于实际值。比如&#xff1a;用某个信号源产生1000个外部触发信号&#xff08;上升沿触发方式&#xff09;给到FPGA输入IO&#xff0c;实际…

PCI 简易通讯控制器有黄色感叹号

一、问题描述 设备管理器中&#xff0c;其他设备中显示 “PCI 简易通讯控制器”驱动未安装&#xff0c;显示黄色感叹号&#xff1a; 二、原因分析 右键该驱动&#xff0c;查看属性ID&#xff0c;显示为&#xff1a; PCI \ VEN_8086&#xff06;DEV_1C3A&#xff06;SUBSYS…

14.3.4 【Linux】使用 LVM thin Volume 让 LVM 动态自动调整磁盘使用率

想像一个情况&#xff0c;你有个目录未来会使用到大约 5T 的容量&#xff0c;但是目前你的磁盘仅有 3T&#xff0c;问题是&#xff0c;接下来的两个月你的系统都还不会超过 3T 的容量&#xff0c; 不过你想要让用户知道&#xff0c;就是他最多有 5T 可以使用就是了&#xff01;…

ECharts 折线图使用相关

一、折线图堆叠设置为不堆叠的方法 官网是这样的&#xff0c;但是不需要这种堆叠形式的如下图&#xff1a; 即&#xff1a;第2条数据值 第1条数据值 第2条数据值 第3条数据值 第2条数据值 第3条数据值 需要改成实际值展示&#xff0c;如下图&#xff1a; 只需要修改stack的…