代码编译

在刚接触java时,我们都知道通过javac命令将java源码文件编译成.class字节码文件,这是由编译器来完成的。
包括泛型擦除属于编译时期的语法糖。

.class字节码文件是跨平台的,也就是不管什么平台的JVM,都可以加载执行。使用javap -c X.class 可以将字节码文件转为可读性较好的格式

类什么时候加载

JVM并不是把所有的字节码文件一下子全加载进内存,Java类的加载是动态的,它并不会一次性将所有类全部加载后再运行,而是保证程序运行的基础类(像是基类)完全加载到jvm中,至于其他类,则在需要的时候才加载。这当然就是为了节省内存开销。

虚拟机规范则是严格规定了有且只有5种情况必须立即对类进行“初始化”(class文件加载到JVM中):

  • 创建类的实例(new 的方式)。访问某个类或接口的静态变量,或者对该静态变量赋值,调用类的静态方法
  • 反射的方式
  • 初始化某个类的子类,则其父类也会被初始化
  • Java虚拟机启动时被标明为启动类的类,直接使用java.exe命令来运行某个主类(包含main方法的那个类)
  • 当使用JDK1.7的动态语言支持时(…)

如何将类加载进JVM

class文件是通过类的加载器装载到jvm中的!
Java默认有三种类加载器:

各个加载器的工作责任:

  • 1)启动类加载器Bootstrap ClassLoader:负责加载$JAVA_HOME中jre/lib/rt.jar里所有的class。由C++实现,不是ClassLoader子类
  • 2)扩展类加载器Extension ClassLoader:负责加载java平台中扩展功能的一些jar包,包括$JAVA_HOME中jre/lib/ext/*.jar或-Djava.ext.dirs指定目录下的jar包
  • 3)应用类加载器App ClassLoader:负责记载classpath中指定的jar包及目录中class

工作过程:

  • 1、当AppClassLoader加载一个class时,它首先不会自己去尝试加载这个类,而是把类加载请求委派给父类加载器ExtClassLoader去完成。
  • 2、当ExtClassLoader加载一个class时,它首先也不会自己去尝试加载这个类,而是把类加载请求委派给BootStrapClassLoader去完成。
  • 3、如果BootStrapClassLoader加载失败(例如在$JAVA_HOME/jre/lib里未查找到该class),会使用ExtClassLoader来尝试加载;
  • 4、若ExtClassLoader也加载失败,则会使用AppClassLoader来加载
  • 5、如果AppClassLoader也加载失败,则会报出异常ClassNotFoundException

其实这就是所谓的双亲委派模型。简单来说:如果一个类加载器收到了类加载的请求,它首先不会自己去尝试加载这个类,而是把请求委托给父加载器去完成,依次向上。

好处:
防止内存中出现多份同样的字节码(安全性角度),比如你不可能自定义一个String类让JVM加载。

特别说明:
类加载器在成功加载某个类之后,会把得到的 java.lang.Class类的实例缓存起来。下次再请求加载该类的时候,类加载器会直接使用缓存的类的实例,而不会尝试再次加载。

自定义类加载器可以实现资源jar隔离,代码保护、热加载等,具体查看自定义类加载器的实际应用场景、类加载器详解

类加载的详细过程

加载器加载到jvm中,接下来其实又分了好几个步骤:

加载,查找并加载类的二进制数据,在Java堆中也创建一个java.lang.Class类的对象。
连接,连接又包含三块内容:验证、准备、初始化。
1)验证,文件格式、元数据、字节码、符号引用验证;
2)准备,为类的静态变量分配内存,并将其初始化为默认值;
3)解析,把类中的符号引用转换为直接引用
初始化,为类的静态变量赋予正确的初始值。

在类加载检查通过后,接下来虚拟机将为新生对象分配内存。

JIT即时编译

但是不同于 C / C++ 语言直接被翻译成机器指令,java字节码文件,它是经过编译器预处理过的一种文件,它本身是二进制文件,但是不可以被系统直接执行,需要虚拟机解释执行,即逐条取出逐条执行。很显然经过解释执行,其执行速度必然会比可执行的二进制字节码程序慢很多。为了提高执行速度,引入了 JIT 技术。

JIT 技术就是把这些Java字节码重新编译优化,生成机器码,让CPU直接执行。这样编出来的代码效率会更高。在运行时 JIT 会把翻译过的机器码保存起来,以备下次使用。这种在运行时按需编译的方式就是Just In Time。

通常,我们不必把所有的Java方法都编译成机器码,只需要把调用最频繁,占据CPU时间最长的方法找出来将其编译成机器码。这种调用最频繁的Java方法就是我们常说的热点方法。热点代码如多次调用的方法、多次执行的循环体。
使用热点探测来检测是否为热点代码,热点探测有两种方式:采样、计数器。目前HotSpot使用的是计数器的方式,当计数器超过阈值溢出了,就会触发JIT编译。

JVM之JIT原理
IBM讲JIT

java代码从编译到加载执行的过程相关推荐

  1. JAVA加载 编译 运行,在Java 7中编译的加载/运行类6

    I am using some client jars in my component the client jars are compiled and run with java 7.I am no ...

  2. java 类编译_Java类编译、加载、和执行机制

    Java类编译.加载.和执行机制 标签: java 类加载 类编译 类执行 机制 0.前言 个人认为,对于JVM的理解,主要是两大方面内容: Java类的编译.加载和执行. JVM的内存管理和垃圾回收 ...

  3. cfile清空文件内容_编译-链接-加载 :ELF文件格式解析

    摘要:对于C++的初学者,经常在程序的编译或者加载过程中遇到很多错误,类似undefined reference to ... 和 GLIBCXX_3.4.20 not found 等.这些错误都涉及 ...

  4. 你知道 Java 类是如何被加载的吗?

    一:前言 最近给一个非Java方向的朋友讲了下双亲委派模型,朋友让我写篇文章深度研究下JVM的ClassLoader,我确实也好久没写JVM相关的文章了,有点手痒痒,涂了皮炎平也抑制不住. 我在向朋友 ...

  5. java中class文件如何加载的_jvm如何加载class文件

    编译期: javac是JDK自带的编译器, 可以将java文件编译为class字节码文件, javap是JDK自带的反编译器,将.class字节码反编译为.java文件,javap -help是jav ...

  6. 面试官:你真的知道 Java 类是如何被加载的吗?

    来自:https://yq.aliyun.com/articles/710407 一:前言 最近给一个非Java方向的朋友讲了下双亲委派模型,朋友让我写篇文章深度研究下JVM的ClassLoader, ...

  7. Java 类中各成分加载顺序和内存中的存放位置

    一.什么时候会加载类? 使用到类中的内容时加载:有三种情况 1.创建对象:new StaticCode(); 2.使用类中的静态成员:StaticCode.num=9; StaticCode.show ...

  8. java的方法什么时候加载,java – JVM什么时候加载类?

    只有当您需要有关该类的信息时,才会加载类. public class SomethingCaller { public static Something something = null; // (1 ...

  9. 深入java虚拟机学习 -- 类的加载机制(续)

    昨晚写 深入java虚拟机学习 -- 类的加载机制 都到1点半了,由于第二天还要工作,没有将上篇文章中的demo讲解写出来,今天抽时间补上昨晚的例子讲解. 这里我先把昨天的两份代码贴过来,重新看下: ...

最新文章

  1. python多次循环输出_函数的Python循环(多次将输出作为输入重用)
  2. 如鲠在喉的电路 - 当BJT的负载和输入都呈电感特性时的 Hartley振荡器
  3. SharpGL学习笔记(一) 平台构建与Opengl的hello World
  4. Logger.getLogger和 LogFactory.getLog
  5. 扩展java.lang.Thread类
  6. Android TabHost中实现标签的滚动以及一些TabHost开发的奇怪问题
  7. 避免Ie下的js缓存问题
  8. protobuf反射详解及应用(pb/json相互转换)
  9. eclipse下搭建SSH整合环境(Struts2+Spring+Hibernate+maven)
  10. VLAN虚拟局域网详解
  11. 微信小程序开发-云数据库添加及获取显示
  12. 一元函数积分学基本计算例题
  13. java毕业设计针织企业外包系统Mybatis+系统+数据库+调试部署
  14. Sublime Text清除历史记录
  15. NPOI 操作Excel学习总结
  16. 瑞萨linux编译环境,瑞萨RZ/A2M Linux4.19系统构建与驱动移植纪实之一:BSP环境搭建...
  17. 物体追踪实战:使用 OpenCV实现对指定颜色的物体追踪
  18. 知乎日报APP:API接口分析
  19. C语言*p、p,p的区别,**p的含义
  20. IC验证培训——实战SV验证学习(lab5)

热门文章

  1. 16进制颜色透明_PPT | 如何快速提取图片颜色之人生太卷
  2. 计算机系教研工作计划,计算机教研室工作计划怎么写
  3. 动作分析 姿态估计_单人或多人的人体姿态骨架估计算法概述
  4. 在WPS中提取出的照片在哪找_WPS技巧 | 找不到合适的配图?教你一招搞定
  5. java 存放大数字_我可以使用什么变量类型在java中保存大量数字(30位数)?
  6. udp java 编程_JAVA 网络编程之UDP编程
  7. java考察代码_一段简单的关于字符串的 Java 代码竟考察了这么多东西
  8. 五十八、深入了解 Java 中的注解和自定义注解
  9. memoryerror: Unable to allocate array with shape (60000, 28, 28) and data ty
  10. 大会剧透 | IDEA大会精彩议题全释放