Java反射、类加载、初始化 【java基础-反射】

目录

一、 先了解一下基本知识:

1.      字节码和机器码是什么,有什么联系

二、反射、类加载器、初始化

2.      反射:

2.1,反射理解:“照镜子”

2.2,Class类常用方法:

2.3,获取某个类的class 实例四种方法:

2.4,反射优点、缺点:

2.5,反射在实际开发中的使用场景:

3,类加载ClassLoader:

3.1,类加载器的一个主要方法:

3.2 类加载器和inputStream 加载配置文件的区别:

3.3 配置文件的路径问题:

3.4  Class.getResource(String path) 与 Class.getClassLoader.getResource (String path) 区别:

4,类的加载机制

4.1 类的加载:

4.2类加载的时机:

4.3 类加载器分类:

4.4 类加载的双亲委派模型:


一、 先了解一下基本知识:

1.      字节码和机器码是什么,有什么联系

二、反射、类加载器、初始化

2.      反射:

2.1,反射理解:

2.2Class类常用方法:

2.3获取某个类的class 实例四种方法:

2.4反射优点、缺点:

2.5,反射在实际开发中的使用场景:

 

3,类加载ClassLoader:

3.1,类加载器的一个主要方法:getResourceAsStream(String str): 获取类路径下的指定文件的输入流

3.2 类加载器和inputStream 加载配置文件的区别:

3.3 配置文件的路径问题:

3.4  Class.getResource(String path) 与 Class.getClassLoader.getResource (String path) 区别:

4,类的加载机制

4.1 类的加载:

4.2类加载的时机

4.3 类加载器分类:

4.4 类加载的双亲委派模型

转载1:机器码和字节码 - 邱明成 - 博客园  《机器码和字节码》

转载2:Java类加载和初始化 - 杨七 - 博客园  《Java类加载和初始化》

转载3:JAVA类加载与初始化顺序_iechenyb专栏-CSDN博客 《JAVA类加载与初始化顺序》

转载4:Java基础----反射 (一) 反射机制、Class类、类的加载和类加载器ClassLoader、反射的使用_yep。的博客-CSDN博客 《Java基础----反射 (一) 反射机制、Class类、类的加载和类加载器ClassLoader、反射的使用》

一、 先了解一下基本知识:

1.      字节码和机器码是什么,有什么联系

机器码:顾名思义,机器可以读懂的码;就是0、1啦;原生码(Native Code),是电脑的CPU可直接解读的数据

字节码:字节码(Bytecode)是一种包含执行程序、由一序列 op 代码/数据对 组成的二进制文件字节码是一种中间码,它比机器码更抽象,需要直译器转译后才能成为机器码的中间代码。(ps:OP (操作码operation code))

举例:java  bytecode; 首先通过java语言编译器编写代码,生成.java 文件,然后编译器实行javac 指令,生成.class 文件(字节码文件),然后jvm 跨平台,在直译器的翻译下生成机器码,让CPU 解读。(ps:编译器的作用:编译器里我们通过高级java 高级语言,编写代码,理由编译器自带的javac 命令,生成字节码.class 文件,然后再通过编译器的java 命令,运行代码,查看结果。)

联系:字节码是一种中间状态(中间码)的二进制代码(文件)。需要直译器转译后才能成为机器码。

二、反射、类加载器、初始化

2.      反射:

2.1,反射理解:照镜子

对象通过反射可以得到的信息:某个类的属性、方法和构造器、某个类到底实现了哪些接口。对于每个类而言,JRE 都为其保留一个不变的 Class 类型的对象。一个 Class 对象包含了特定某个结构(class/interface/enum/annotation/primitive type/void/[])的有关信息。

概念:Reflection(反射)是被视为动态语言的关键,反射机制允许程序在执行期借助于Refle反射的API取得任何类的内部信息,并能直接操作任意对象的内部属性及方法。

在Object类中定义了public final Class getClass()方法,方法返回值的类型是一个Class类。
Class类是Reflection的根源,针对任何你想动态加载、运行的类,唯有先获得相应的Class对象。

2.2Class类常用方法:

2.3获取某个类的class 实例四种方法:

法1:  // 已知具体的类,调用运行时类的属性:.class;它主要应用于原始数据类型,并且仅在我们知道类的名称时才使用。要创建的Class对象的类名在编译时确定。    
     Class<?> clazz = String.class;  
法2: //已知某个类的实例,调用该实例的getClass()方法获取Class对象
    String str = new String("string");
    Class c3 = str.getClass();
法3:调用Class的静态方法:forName(String classPath)
    Class<?> clazz = Class.forName(“某个类的类名(路径)”);
法4:方式四:使用类的加载器:ClassLoader
   ClassLoader classLoader = ReflectionTest.class.getClassLoader();
   Class<?> clazz4 = classLoader.loadClass("reflection_mechanism.Person");

2.4反射优点、缺点:

优点:提高了程序的灵活性和扩展性,降低模块的耦合性;例如通过反射机制可以让程序创建和控制任何类的对象,无需提前硬编码目标类;反射是框架的灵魂,使用反射可以避免将代码写死在框架中。

缺点:性能问题:反射相当于一系列解释操作,通知jvm要做的事情,性能比直接的java代码要慢很多。把本来应该在项目启动阶段做的事情,延迟到了项目运行阶段来做。这样就增加了项目运行阶段的系统开销。安全限制:使用反射技术要求程序必须在一个没有安全限制的环境中运行。因为有内部的暴露。

2.5,反射在实际开发中的使用场景:

♢反射使用不好,对性能影响比较,一般项目中很少直接使用,主要用在底层框架中。使用反射机制,①模块开发,通过反射调用对应字节码;②动态代理模式;③spring框架、Hibernate框架等;

反射是框架设计的灵魂。

举例:

  • ① 用 IoC 来注入和组装 bean;
  • ②工厂模式:Factory类中用反射的话,添加了一个新的类之后,就不需要再修改工厂类Factory
  • ③数据库JDBC中通过Class.forName(Driver).来获得数据库连接驱动;
  • ④动态代理、面向切面、bean 对象中的方法替换与增强,也使用了反射;
  • ⑤定义的注解,也是通过反射查找

ps:什么是IoC?--- “控制反转”, 获的对象的过程被反转了,依赖注入。 控制权的转移,应用程序本身不负责依赖对象的创建和维护,而是有外部容器的创建和维护。例如将对象的依赖交给配置文件来配置

 

3,类加载ClassLoader:

3.1,类加载器的一个主要方法:

getResourceAsStream(String str): 获取类路径下的指定文件的输入流

3.2 类加载器和inputStream 加载配置文件的区别:

类加载器作用:

加载“.classpath”的资源文件,例如xml、properities文件。注意:该方式只能读取类路径(.classpath)的配置文件

InputStream 读取配置文件:

注:该方式的优点在于可以读取任意路径下的配置文件

3.3 配置文件的路径问题:

类加载器作用:加载“.classpath”的资源文件,例如xml、properities文件

注意:该方式只能读取类路径(.classpath)的配置文件

ps:查看eclipse中的.classpath 文件:Window-》show View-》Navigator(Deprecated)

   配置文件的路径是个疑惑!!!,从使用相对路径时频繁报错!!!,其实Class.getClassLoader.getResource (String path) 默认是从.classpath根下获取。

        

//PolymorphicFunction这一行的完整代码 pro.load(HeroFactories.class.getClassLoader().getResourceAsStream("PolymorphicFunction/Pro.properties"));

3.4  Class.getResource(String path) 与 Class.getClassLoader.getResource (String path) 区别:

Class.getResource(String path)

☆ path不以'/'开头时,默认是从此类所在的包下取资源;

path'/'开头时,则是从项目的ClassPath根下获取资源

class.getResource("/") == class.getClassLoader().getResource("")

Class.getClassLoader.getResource (String path) 

♢默认是从ClassPath根下获取,path不能以’/'开头,根是src(bin),classPath文件到配置文件xml或者properties文件;

 path不能以'/'开头path是指类加载器的加载范围,在资源加载的过程中,使用的逐级向上委托的形式加载的,'/'表示Boot ClassLoader,类加载器中的加载范围,因为这个类加载器是C++实现的,所以加载范围为null。

4,类的加载机制

4.1 类的加载:

   类的加载:指的是将类的.class字节码文件中的二进制数据读入到jvm内存中,将其放在运行时数据区的方法区内,然后在堆区创建一个 java.lang.Class对象,用来封装类在方法区内的数据结构。

4.2类加载的时机:

类从被加载到虚拟机内存中开始,到卸载出内存为止,整个生命周期包括以下7个阶段:加载、验证、准备、解析、初始化、使用、卸载。

 其中验证、准备、解析3个部分统称为连接。 因此生命周期可以简记为:加载、连接(验、准、解)、初始化、使用、卸载(加连初使卸)

4.3 类加载器分类:

加载器主要有四种:

①   jvm启动类加载器bootstrap loader,用c++实现为jvm的一部分(仅指sun的hotspot),负责 JAVA_HOME/lib下面的类库中的类的加载,这个加载器,java程序无法引用到。

②   扩展类加载器Extension Loader,由sun.misc.Launcher$ExtClassLoader类实现,可在java中使用,负责JAVA_HOME/lib/ext 目录和java.ext.dir目录中类库的类的加载。

③   应用系统类加载器Application System Loader,由sun.misc.Louncher$AppClassLoader实现,负责加载用户类路径中类库中的类,如果没有使用自定义的加载器,这个就是默认的 加载器!

④   用户自定义加载器 自己定义从哪里加载类的二进制流。

4.4 类加载的双亲委派模型:

各个加载器都是先委托自己的父加载器加载类,若确实没加载到再自己来加载,于是java默认的类查找加载顺序是自顶向下的,树状结构。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

伟庭大师兄

你的鼓励是我最大的动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值