Java中类的加载器和反射

3、获取class 文件中的成员

(1) 使用反射获取无参的构造方法并运行

(2) 使用反射获取有参的构造方法并运行

(3) 反射获取构造方法并运行的快捷方式

(4) 反射获取私有构造方法并运行(暴力反射)

(5) 反射获得成员变量并修改

(6) 反射获得成员方法并运行

(7) 反射泛型擦除

(8) 反射通过配置文件运行实现


一、类加载器

======

  • 负责将 .class 文件加载到内存中,并为之生成对应的 class 对象

1、类的加载


当程序要使用某个类时,如果该类还未被加载到内存中,则系统会通过加载,连接,初始化三个步骤来实现对这个类进行初始化

  • 加载:将 class 文件读入内存,并为之创建一个 class 对象,任何类被使用时系统都会建立一个 class 对象

  • 连接:验证是否有正确的内部结构,并和其他类协调一致,为类的静态成员分配内存,并设置默认初始化值,将类的二进制数据中的符号引用替换为直接引用

  • 初始化:创建对象等

2、类初始化时机(何时加载到内存中)


  • 创建类的实例对象时

  • 类的静态变量或为静态变量赋值

  • 类的静态方法

  • 使用反射方式来强制某个类或接口对应的 java.lang.Class 对象

  • 直接使用 java.exe 命令来运行某个主类

3、类加载器的组成


  • Bootstrap ClassLoader:根类加载器,也被称为引导类加载器,负责Java核心类的加载,如:System,String等

  • Extension ClassLoader:扩展类加载器,负责JRE的扩展目录中jar包的加载

  • System ClassLoader:系统类加载器,负责在jvm启动时加载来自Java命令的class文件,以及classpath环境变量所指定的jar包和类路径

二、反射

====

Java中反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为Java语言的反射机制

1、反射原理步骤


  • 类加载到内存

  • 加载器自动为.class 文件创建一个对象

  • 在自己的程序中获取到.class 文件

2、获取一个类的 class 文件对象的三种方式


以获取Person类的class文件对象为例,这三种方法获得的都是同一个对象

  • 对象获取:调用 Person 类的父类方法 getClass()

  • 类名获取: 每个类型,包括基本类型和引用类型,都会赋予这个类型一个静态的属性,属性名字为class

  • Class 类的静态方法获取:Class 类的静态方法获取forName(字符串的类名)包名**.**类名

public static void main(String[] args) throws ClassNotFoundException {

//1.对象获取,调用Person类的父类方法 getClass()

Person P = new Person();

Class C = P.getClass();

System.out.println©;

//2.类名获取

Class C1 = Person.class;

System.out.println(C1);

//3.类的静态方法获取

Class C2 = Class.forName(“myFansheClass.Person”);

System.out.println(C2);

}

3、获取class 文件中的成员


(1) 使用反射获取无参的构造方法并运行

  • Constructor getConstructor():获取指定的空参构造方法

  • Constructor[]  getConstructors(): 获取class文件对象中的所有公共的构造方法,返回的是构造方法的数组

  • newInstance():运行空参构造函数,可以赋值给 object 父类进行多态调用

public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {

//类的静态方法获取

Class C = Class.forName(“myFansheClass.Person”);

System.out.println©;

//获取class文件对象中的所有公共的构造方法

Constructor[] Cons = C.getConstructors();

for(Constructor con : Cons)

{

System.out.println(con);

}

//获取指定的构造方法,空参的

Constructor Co = C.getConstructor();

System.out.println(Co);

//运行空参构造方法,赋值给父类object多态调用

Object obj = Co.newInstance();

System.out.println(obj);

//将obj强转即可调用Person类中的方法和变量

Person p = (Person)obj;

p.Study();

System.out.println(p.age);

}

(2) 使用反射获取有参的构造方法并运行

  • Constructor getConstructor(Class<?>… parameterTypes):获得指定的构造方法,传递要获取的构造方法的参数列表

  • Object newInstance(Class<?>… parameterTypes):运行构造方法,传递可变参数

public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {

//类的静态方法获取

Class C = Class.forName(“myFansheClass.Person”);

System.out.println©;

//Constructor getConstructor(Class<?>… parameterTypes)获取构造方法

Constructor Con = C.getConstructor(String.class,int.class);

System.out.println(Con);

//运行构造方法,传递可变参数

Object obj = Con.newInstance(“Tom”,18);

System.out.println(obj);

}

(3) 反射获取构造方法并运行的快捷方式

  • 被反射的类必须有空参构造函数

  • 构造方法必须是 public 权限

public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {

//类的静态方法获取

Class C = Class.forName(“myFansheClass.Person”);

System.out.println©;

//反射获取构造方法并运行的快捷方式

Object obj = C2.newInstance();

System.out.println(obj);

}

(4) 反射获取私有构造方法并运行(暴力反射)

  • 不推荐,破坏了程序的封装性和安全性

  • Constructor getConstructor():获取指定参数的构造方法

  • Constructor类的父类AccessibleObject类的方法setAccessible(boolean b),参数为true的时候能取消访问检查

public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {

//类的静态方法获取

Class C = Class.forName(“myFansheClass.Person”);

System.out.println©;

//反射获取私有构造方法并运行

//1、Constructor getConstructor()获取指定参数的构造方法

Constructor con = C.getDeclaredConstructor(int.class,String.class);

//2、Constructor类的父类AccessibleObject类的方法setAccessible(boolean b),参数为true的时候能取消访问检查

con.setAccessible(true);

Object obj = con.newInstance(12,“Tim”);

System.out.println(obj);

}

(5) 反射获得成员变量并修改

  • Field[] getFields():获取成员变量Class类的方法getFields() class文件中所有公共的成员变量,返回 Field[] 数组,Field 类是描述类成员变量的类

  • Field[] getField():获取指定的成员变量,通过 set() 方法来修改对象的成员变量

  • Field[] getDeclaredFields():获得私有成员变量

public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {

//类的静态方法获取

Class C = Class.forName(“myFansheClass.Person”);

自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。

深知大多数Java工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年Java开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Java开发知识点,真正体系化!

由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!

如果你觉得这些内容对你有帮助,可以扫码获取!!(备注Java获取)

img

总结

面试建议是,一定要自信,敢于表达,面试的时候我们对知识的掌握有时候很难面面俱到,把自己的思路说出来,而不是直接告诉面试官自己不懂,这也是可以加分的。

以上就是蚂蚁技术四面和HR面试题目,以下最新总结的最全,范围包含最全MySQL、Spring、Redis、JVM等最全面试题和答案,仅用于参考

一份还热乎的蚂蚁金服面经(已拿Offer)面试流程4轮技术面+1轮HR

《一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码》点击传送门即可获取!
mg-community.csdnimg.cn/images/e5c14a7895254671a72faed303032d36.jpg" alt=“img” style=“zoom: 33%;” />

总结

面试建议是,一定要自信,敢于表达,面试的时候我们对知识的掌握有时候很难面面俱到,把自己的思路说出来,而不是直接告诉面试官自己不懂,这也是可以加分的。

以上就是蚂蚁技术四面和HR面试题目,以下最新总结的最全,范围包含最全MySQL、Spring、Redis、JVM等最全面试题和答案,仅用于参考

[外链图片转存中…(img-jb4JYfpQ-1711983830610)]

《一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码》点击传送门即可获取!

  • 12
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值