栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

JVM(一) - 基础

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

JVM(一) - 基础

Java8官方文档:https://docs.oracle.com/javase/8/docs/

一、Java SE Platform

JDK(Java Development Kit):Java开发工具包。JDK是整个 Java 开发的核心,它集成了JRE 和一些好用的小工具(如Javac、JConsole、VisualVM等)。提供用户开发Java程序,内部Javac编译Java文件到Class文件、JConsole调试、VisualVM分析工具、javadoc文档。需要编写、编译Java程序需要用到JDK。

JRE(Java Runtime Environment):Java运行时环境。主要包含两个部分:JVM 的标准实现和 Java 的一些基本类库(如Beans、JDBC等),相比与JVM就是多了一些java类库。提供用户运行Java程序,运行Java程序只需要JRE。

JVM(Java Virtual Machine):Java虚拟机。执行Class文件的字节码解析转化为机器码。提供一套JVM字节码运行的规范,不同的厂商不同平台提供其JVM。目前主流的JVM虚拟机是HotSpot。

JDK为什么会集成了JRE?

JDK中一些可执行文件,如javac内部调用的其实是 JDK 中 lib 目录中的 tools.jar 中 com.sun.tools.javac.Main 类,也就是说这些工具只是入口而已,实际本身由Java编写,所以在JDK目录下的JRE既提供了自身工具的运行时环境,也提供了用户编写Java程序的运行时环境。

Java跨平台使用,一次编写,多处运行?

Java同一套代码可以在不同的系统不同的硬件上执行相同的效果,核心是因为JVM,JVM提供一套字节码运行的规范,不同平台有不同的实现。

二、Java Virtual Machine

虚拟机(Virtual Machine)就是提供虚拟计算机作用的软件,用来执行一些虚拟计算机指令。可分为两类:

  • 系统虚拟机:完全是对物理计算机的仿真,提供一个可运行完整操作系统的软件平台。如Visual Box、VMware;
  • 程序虚拟机:专门为执行单个计算机程序而设计,如Java虚拟机用来执行Java字节码指令。

1、Java虚拟机
  • 执行二进制字节码的虚拟计算机,装载字节码到其内部,解释/编译为对应平台上的机器指令执行。但其运行的节码也不一定由Java语言编译而成;
  • JVM平台的各种语言可以共享Java虚拟机带来的跨平台性、优秀的垃圾回收器,以及可靠的即时编译器;
  • Java技术的核心就是Java虚拟机,因为所有的java程序都运行在Java虚拟机内部。

JVM在整个JDK(java 运行环境)中处于最底层,位于操作系统之上,负责与操作系统的交互(并不直接与硬件交互),用来屏蔽操作系统环境,提供一个完整的、跨平台的Java运行环境。

2、Java程序执行全流程

前端编译器:把java代码转成字节码,与JVM无关。如Javac。

JVM执行引擎:把字节码转成机器码。如字节码解释器、JIT即时编译器。

流程图如下:

3、Jvm指令执行方式

指令执行有两种方式:基于栈的指令集执行 和 基于寄存器的指令集执行,Jvm采用的是基于栈的指令集执行。

基于栈式方式的特点:

  • 设计和实现更简单,适用于资源受限的系统
  • 不需要硬件支持,可移植性更好,更好实现跨平台
  • 基于栈式架构的指令集却以零地址指令为主
  • 指令流中的指令大部分是零地址指令,其执行过程依赖于操作栈
  • 通常要比基于寄存器的指令集数量要多,执行速度要慢一些

基于寄存器方式的特点:

  • 指令集与硬件架构紧密关联的,无法做到可移植
  • 花费更少的指令去完成一项操作
  • 指令集是直接由CPU来执行的,它是在高速缓冲区进行执行的,速度要快很多
  • 基于寄存器架构的指令集往往都以一地址指令、二地址指令、三地址指令为主

执行3+1,通过Jclasslib查看字节码其指令分别如下:

public static void main(String[] args) {
    int v = 3 + 1;
    System.out.println(v);
}
// 字节码
 0 iconst_3	// 将常量3入栈
 1 istore_1	// 弹出操作数栈顶元素,并把元素的值复制到本地变量表索引为1的位置
 2 iconst_2	// 将常量2入栈
 3 istore_2	// 弹出操作数栈顶元素,并把元素的值复制到本地变量表索引为2的位置。
 4 iload_1		// 从本地变量表中索引为1的值压入操作数栈
 5 iload_2		// 从本地变量表中索引为2的值压入操作数栈
 6 isub		// 弹出操作数栈最上层的两个元素,进行减操作(3-2),将结果1压入操作数栈
 7 istore_3	// 弹出操作数栈顶元素常量1,并把元素的值复制到本地变量表索引为3的位置
 8 getstatic #2 	// 在常量池中找到索引为2的静态方法,即System.out
11 iload_3		// 从本地变量表中索引为3的值(即1)压入操作数栈
12 invokevirtual #3 	// 方法调用,找到常量池中找到索引为3的方法,生成新的栈帧(分配 locals、stack等),传递参数,执行新栈帧中的字节码
15 return

 基于寄存器指令:

mov eax,3	// 将3放入寄存器,
sub eax,2 	// 后面跟一个参数2,在现有的寄存器上减去2,在把结果放回寄存器。

三、JVM内存模型

Jvm内存模型图,具体分析见内存模型章节。

四、JVM生命周期 虚拟机的启动

通过引导类加载器(bootstrap class loader)创建一个初始类(initial class)来完成的,这个类是由虚拟机的具体实现指定的。

虚拟机的执行
  • 运行中的Java虚拟机有着一个清晰的任务:执行Java程序
  • 程序开始执行时他才运行,程序结束时他就停止

虚拟机的退出

如下的几种情况:

  • 程序正常执行结束
  • 程序在执行过程中遇到了异常或错误而异常终止
  • 由于操作系统出现错误而导致Java虚拟机进程终止
  • 某线程调用Runtime类或System类的exit方法,或Runtime类的halt方法,并且Java安全管理器也允许这次exit或halt操作
  • 除此之外,JNI(Java Native Interface)规范描述了用JNI Invocation API 来加载或卸载Java虚拟机时,Java虚拟机的退出情况

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/988860.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号