首页 > java 中 bean 的生命周期

java 中 bean 的生命周期

java 中 bean 的生命周期

本篇中会对涉及到的知识点皆做出描述:

首先,我们先了解先虚拟机的类加载机制:

 虚拟机把描述类的数据从Class 文件中加载到内存,并对数据进行校验、转换解析和初始化,最终形成可以被虚拟机直接使用的 java 类型,这便是虚拟机的类加载机制。

也就是说,一个文本.java 文件要运行起来:它首先要经过编译成为 Class 文件(字节码文件),然后被虚拟机加载读入内存,接着虚拟机首先对其中的数据进行校验

 

一个类从被加载的虚拟机内存中开始到卸载出内存为止(java 类的卸载并不能人为主动卸载,只能通过 JVM 的垃圾回收来卸载。没有像 C 中析构函数那样的东西)经历的有:

加载

加载阶段虚拟机完成三件事情:

1.通过一个类的全限定名称来获取定义此类的二进制字节流

2.将这个字节流所代表的静态储存结构转化为方法区的运行时数据结构。

3.在内存中生成一个代表这个类的java.lang.Class对象,作为方法区这个类的各种数据的访问入口

验证

验证阶段大致完成4个阶段的检验动作:

1.文件格式验证

该验证阶段时基于二进制字节流的,通过这个阶段验证后字节流才会进入内存的方法区中进行存储。而后面的3个验证阶段全部是基于方法区的存储结构进行的。

2.元数据验证:比如校验类的继承关系是否合法

3.字节码验证:例如保证跳转指令不会跳转到方法体之外的字节码指令上。

4.符号引用验证:例如符号引用中通过字符串描述的全限定名称是否能找到对应的类

准备

正式为类变量分配内存并设置类变量初始值,变量所使用的内存都将在方法区中进行分配。(这个时候进行内存分配的仅包括类变量既被 static 修饰的变量而不包括实例变量。实例变量会在对象实例话时随着对象一起分配在 java 堆中

这时分配的初始值往往都时零值,实际代码中定义的值在初始化阶段才会赋予。(final修饰的除外,会在此阶段赋值

解析

解析阶段是将常量池内的符号引用替换为直接引用的过程。

1.类或接口的解析

比如当前所在A类,在A类中引用了B类且B类从未被解析过。

(1)如果B不是一个数组类型,那虚拟机会把代表B的全限定名传递给A类的加载器去加载类B。

(2)如果B是一个数组类型,并且数组的元素为对象。那么虚拟机会按(1)中的方式去加载数组的元素类型。接着虚拟机会生成一个代表此数组维度和元素的数组对象。

(3)如果上面的步骤没有异常,那么B在虚拟机中实际上已经成为一个有效的类或接口了,但在解析完成之前还需进行符号引用验证,确认A是否具备对B的访问权限。如不具备则抛出java.lang.IllegalAccessError 非法访问异常。

2.字段解析

(1)如果A类本身包含了简单名称和字段描述符都与目标相匹配的字段,则返回这个字段的直接引用,查找结束。

(2)否则,如果在A中实现了接口,将会按照继承关系从下往上递归搜索各个接口的它的的父接口,如果接口中包含了简单名称和字段描述符都与目标相匹配的字段,则返回这个字段的直接引用,查找结束。

(3)否则,如果A不是java.lang.Object的话,将会按照继承关系从下往上递归搜索其父类。如果在父类中包含了简单名称和字段描述符都与目标相匹配的字段,则返回字段查找结束。

(4)否则,查找失败。

如果查找成功了还会对该字段进行权限验证,如发现不具备对字段的访问权限,将抛出java.lang.IllegalAccessError异常。

3.类方法解析

4.接口方法解析

初始化

进行初始化的条件:

1.当遇到 newgetstaticputstatic或invokestatic这4调字节码指令时,如没有进行过初始化则需要出发初始化。

           既 当你用 new 实例化一个对象时  读取或者设置一个类的静态字段时 (这里有一种静态字段除外:用 final 修饰,既已在编译期把结果放入常量池的静态字段除外)   调用一个类的静态方法的时候 (同样,也是被 fianl 修饰的除外)

          总结来说,第一点就是 当用 new 实例化一个对象时 以及 用到没有被 final 修饰的类的静态字段或方法时 就会触发初始化

2.使用 反射包的方法对类进行反射调用的时候

           这个更好理解,反射调用类的方法是需要类的实例的,得到类的实例便要经过初始化过程。

3.当初始化一个类时,如果发现其父类还未初始化,则要先触发其父类的初始化(接口稍有区别,只有在真正使用到父类接口的时候才会去初始化)

4.当虚拟机启动时会先初始化主类(既包含main() 方法的那个类)

5.当使用JDK1.7的动态语言支持时。如果 java.lang.incoke.MethodHandle 实例最后的解析结果 REF_getStatic、REF_putStatic、REF_invokeStatic 的方法句柄,并且这个方法句柄所对应的类没有进行过初始化,则需要先触发其初始化。

(了解java.lang.incoke.MethodHandle)

 有且只有这五种情况才会触发初始化。这五种为主动引用。除此之外所有引用类的方式都不会触发初始化,这些称为被动引动。

一下为被动引用:

1.通过子类引用父类的静态字段。

2.通过数组定义来引用类,不会触发此类的初始化

3.常量在编译阶段存入调用类的常量池中,本质上并没有直接引用到定义常量的类,所以不会触发定义常量的类的初始化。

卸载

这七个阶段。其中,验证、准备、解析三个部分又被称为连接。

 

这几个阶段的顺序:

首先 加载、验证、准备、初始化和卸载这五个过程是确定的(使用不用多说)。

1.加载------>2.验证------>3.准备------->............?初始化.........6.使用------->.7.卸载

解析和初始化这两个的顺序是不确定的。某些情况下解析可以在初始化之后再开始,以支持java 的运行时绑定,既动态绑定。(而动态绑定最为容易想到的例子就是多态)所以,可以说java 多态也是因为解析步骤可以在初始化之后。

而确定的这五个过程也并不是等一个完成才进行下一个的,这些阶段通常都是互相交叉混合的进行的,通常会在一个阶段执行的过程中调用、激活另一个阶段。

 

posted on 2018-03-21 21:23 code前行 阅读(...) 评论(...) 编辑 收藏

转载于:https://www.cnblogs.com/codefeng/p/8598050.html

更多相关:

  • Math.max(...arr);//返回数组最大值 Math.min(...arr);//返回数组最小值Math.max(...objArr.map(o => o.最值字段名));//返回对象数组最大值 Math.min(...objArr.map(o => o.最值字段名));//返回对象数组最小值objArr.sort((pre...

  • 有关函数的官方文档:https://onlinehelp.tableau.com/current/pro/desktop/zh-cn/functions_functions_string.htm 注意事项: 1.记录数:是Tableau自动给每行观测值赋值为1。 2.维度的字段,是不能用于计算的,若是要用于计算,则需要转成度量。 3...

  • 1:删除   连接数据库:新建连接数据库,或者应用转换中已经定义好的数据库。 目标模式:指什么现在还不明确,集群模式?子服务器模式?--要写入数据的表的Schema名称。允许表名中包含“.”是很重要的。  目标表:指定删除记录所对应的表。   提交记录数量:提交之前要改变(删除)的行数   表字段:来源于目标表中的字段。   流字段:...

  • 前言: 前面两篇都是大体介绍流程,有一些配置细节,没有细说,这里用一篇补上。 1、Excel配置项 起始行索引、列头跨行数: 对于自定义的Excel导入模板(有时候模板是由客户提供,模板的规则很乱)比如模板里前面是一些说明,中间是列头,下面还带有数据和说明格式。通过配置起始行索引,以及列头跨行数(0或1都代表一行),则可以解决此类...

  • 1.查询频繁 2.区分度高 例如:数据库表字段:sex 存储:男女,区分度就不高。 3.长度小 索引的长度直接影响索引文件的大小,影响增删改的速度,并间接影响查询速度。 4.尽可能覆盖常用字段   转载于:https://www.cnblogs.com/mingliangzhu/p/6972045.html...

  • 原文出处: 韩昊    1 2 3 4 5 6 7 8 9 10 作 者:韩 昊 知 乎:Heinrich 微 博:@花生油工人 知乎专栏:与时间无关的故事   谨以此文献给大连海事大学的吴楠老师,柳晓鸣老师,王新年老师以及张晶泊老师。   转载的同学请保留上面这句话,谢谢。如果还能保留文章来源就更感激不尽了。 我保证这篇文章...

  • 原文出处: 韩昊   我保证这篇文章和你以前看过的所有文章都不同,这是 2012 年还在果壳的时候写的,但是当时没有来得及写完就出国了……于是拖了两年,嗯,我是拖延症患者…… 这篇文章的核心思想就是: 要让读者在不看任何数学公式的情况下理解傅里叶分析。 傅里叶分析不仅仅是一个数学工具,更是一种可以彻底颠覆一个人以前世界观的思维...

  • 很多Linux高手都喜欢使用screen命令,screen命令可以使你轻松地使用一个终端控制其他终端。尽管screen本身是一个非常有用的工具,byobu作为screen的增强版本,比screen更加好用而且美观,并且提供有用的信息和快捷的热键。 想象一下这样一个场景:你通过Secure Shell(ssh)链接到一个服务器,并...

  • NarrowbandPrimary Synchronization Signal时域位置每1个SFN存在一个NPSSSFNSubframeSymbol长度每个SFN5最后11个symbol11个symbols频域位置NB-IOT下行带宽固定180kHz,一个PRB,12个子载波。...

  •  [h1]反斜杠只能够阻止一个字符  [h2]位于键盘的左上角,和~公用一个键。...