JVM体系

JVM是一种虚拟的计算机,它模拟了一个完整的硬件系统,并运行在一个完全隔离的环境中。这意味着JVM可以看作是一个在操作系统之上的计算机系统,与VMware、Virtual Box等虚拟机类似。JVM的设计目标是提供一个安全、可靠、高效且跨平台的运行环境,使得Java程序可以在任何装有JVM的平台上运行,实现“一次编译,多次运行”的特性。

JVM的体系架构主要包括以下几个部分:

类加载器(ClassLoader)

类加载器负责从文件系统或网络中加载.class文件,然后将其转换成Java类,以供JVM执行。JVM定义了三种类加载器:启动类加载器(Bootstrap ClassLoader)、扩展类加载器(Extension ClassLoader)和应用程序类加载器(Application ClassLoader)。此外,用户还可以自定义类加载器。

类加载器的工作原理可以概括为三个步骤:加载、链接和初始化。

加载:类加载器首先会检查这个类的字节码文件是否已经被加载过,如果尚未加载,系统会初始化一个新的类。加载类的方式主要是从文件系统中读取.class文件,或者从网络获取.class文件,或者从zip、jar等归档包中读取.class文件,或者从其他来源动态生成.class文件。然后,类加载器将这个字节码文件的内容加载到内存中,并生成一个代表这个类的java.lang.Class对象,这个对象会被放入到Java堆内存中。

链接:链接包含验证、准备和解析三个阶段。验证是为了确保被加载的类文件信息符合JVM规范,没有安全方面的问题;准备是给类的静态变量分配内存,并设置默认的初始值;解析是将符号引用转换为直接引用,也就是将类中的符号引用(比如方法名)转换为实际的内存地址引用。

初始化:初始化阶段是执行类构造器方法的过程。此方法由编译器自动收集类中的所有类变量的赋值动作和静态代码块集合来生成的。

JVM提供了三种类型的类加载器:启动类加载器(Bootstrap ClassLoader)、扩展类加载器(Extension ClassLoader)和应用程序类加载器(Application ClassLoader)。

启动类加载器:这是最顶层的加载类,主要加载核心类库,如rt.jar、resources.jar、charsets.jar等。它并不继承自ClassLoader,因为它在Java程序运行之前就已经被加载了。

扩展类加载器:这是启动类加载器的子加载器,它的父加载器是启动类加载器。它主要负责加载Java的扩展类库。

应用程序类加载器:这是扩展类加载器的子加载器,它的父加载器是扩展类加载器。它主要负责加载应用程序的类路径(CLASSPATH)上的类库。

这三种类加载器之间存在层级关系,形成了一种双亲委派模型。当一个类加载器收到了类加载请求,它首先不会自己先去加载,而是把这个请求委派给父类加载器去完成,每一个层次的类加载器都是如此,因此所有的加载请求最终都应该传送到顶层的启动类加载器中。只有当父类加载器无法完成这个加载请求(它的搜索范围中没有找到所需的类)时,子加载器才会尝试自己去加载。

类加载器的作用主要是实现类的动态加载,即只有在程序运行时才根据需要加载相应的类,而不是一次性加载所有的类。这种机制有助于减少程序启动时的内存开销,同时也可以避免加载无用的类,提高程序的运行效率。

运行时数据区

这是JVM在执行Java程序时使用的内存区域,主要包括方法区、堆、Java栈、程序计数器和本地方法栈。其中,方法区和堆是线程共享的,而Java栈、程序计数器和本地方法栈则是线程私有的。

方法区(Method Area)

方法区也被称为元空间(Metaspace)。它用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译后的代码等数据。方法区是硬盘和CPU的中间桥梁,承载着操作系统和应用程序的实时运行。在HotSpot虚拟机中,方法区是线程共享的内存区域,它随着虚拟机的启动而创建,随着虚拟机的退出而销毁。

堆区(Heap)

堆区是垃圾收集器管理的主要区域,也被称为“垃圾收集堆”。堆区是线程共享的,它分为新生代和老年代。新生代主要存放新创建的对象,而老年代则存放存活时间较长的对象。堆区是JVM所管理的最大一块内存区域,几乎所有的对象实例都会在这里分配内存。

栈区(Stack)

每个线程在创建时都会创建一个虚拟机栈,每个方法在执行时都会创建一个栈帧(Stack Frame)用于存储局部变量表、操作数栈、动态链接、方法出口等信息。栈区是线程私有的,每个线程都有自己的栈区,它的生命周期与线程的生命周期一致。栈区分为Java栈和本地方法栈。Java栈用于执行Java方法,而本地方法栈则用于执行native方法。

程序计数器(Program Counter)

程序计数器是一块较小的内存空间,也是运行速度最快的存储区域。它是线程私有的,每个线程都有一个自己的程序计数器,其生命周期与线程的生命周期一致。程序计数器用于指示当前线程所执行的字节码的行号指示器,字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要执行的字节码指令。它是程序控制流的指示器,分支、循环、跳转、异常处理和线程恢复等功能都需要依赖这个计数器完成。

执行引擎

执行引擎负责执行JVM中的字节码。它采用即时编译(JIT)技术,将字节码编译成机器码,以提高执行效率。此外,执行引擎还负责执行本地方法,即使用其他语言(如C和C++)编写的代码。

执行引擎主要包含以下几个部分:

解释器

当JVM启动时,解释器会根据预定义的规范对字节码进行逐行解释执行。解释器会“翻译”每条字节码指令为对应平台的本地机器指令,并执行这些指令。这种方式实现了Java的跨平台特性,因为字节码是平台无关的,只要有对应的解释器,就可以在任何平台上执行。

即时编译器(JIT Compiler)

即时编译器是另一种执行字节码的方式。与解释器不同,JIT编译器会将字节码直接编译成和本地机器平台相关的机器语言。这种方式可以提高程序的执行效率,因为编译后的机器代码通常比解释执行的代码运行得更快。JIT编译器通常会在程序运行时,根据程序的热点代码(频繁执行的代码)进行编译优化,以提高程序的性能。

执行引擎的工作过程如下:

指令获取

执行引擎在执行过程中,会根据程序计数器(Program Counter)来确定下一条需要执行的字节码指令。程序计数器是一个较小的内存空间,它记录了当前线程所执行的字节码的行号。每当执行完一项指令操作后,程序计数器就会更新为下一条需要被执行的指令地址。

指令执行

获取到指令后,执行引擎会将其解释或编译为本地机器指令,并在硬件上执行这些指令。这个过程可能会涉及到对本地方法栈的调用,以执行native方法(使用其他语言编写的代码)。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/673923.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

vue安装依赖--save-dev和--save的区别是啥

就是使用这2种方法后就发现哪种都可以 dependencies:运行时的依赖,发布后,即生产环境下还需要用的模块 devDependencies:开发时的依赖。里面的模块是开发时用的,发布时用不到它。 作为一名后端开发人员,我…

Vue3中路由配置Catch all routes (“*“) must .....问题

Vue3中路由配置Catch all routes (“*”) must …问题 文章目录 Vue3中路由配置Catch all routes ("*") must .....问题1. 业务场景描述1. 加载并添加异步路由场景2. vue2中加载并添加异步路由(OK)3. 转vue3后不好使(Error)1. 代码2. 错误 2. 处理方式1. 修改前2. 修…

8_姿态的其他描述及一般坐标系映射

1.机器人姿态的其他表示方法 前面说的用33矩阵矩阵描述姿态,9个元素,6个约束条件,实际上只有3个独立元素。即用3个独立元素即可描述机器人姿态。常用的有RPY角,欧拉角和四元数。 1.1 RPY角 RPY角是船舶在海上航行时常用的一种姿态…

基于java+springboot+vue实现的高校物品捐赠管理系统(文末源码+Lw)23-151

第1章 绪论 当前的网络技术,软件技术等都具备成熟的理论基础,市场上也出现各种技术开发的软件,这些软件都被用于各个领域,包括生活和工作的领域。随着电脑和笔记本的广泛运用,以及各种计算机硬件的完善和升级&#xf…

构建你的Python知识体系:一份详尽的Python知识图谱指南

序言:知识地图的重要性 当我们谈论Python知识图谱时,脑海中浮现的是一幅层次分明、结构清晰的知识网络,它将Python语言的各个核心概念、技术栈以及应用场景有机地连接起来,形成一个完整的知识生态系统。掌握这份图谱不仅有助于新…

gitee_pingo集成图床

利用Gitee搭建免费图床(详细教程)_gitee搭建图床-CSDN博客

Elasticsearch基于分区的索引策略

分区索引,或者更常见的说法,基于分区的索引策略,是一种按照特定规则(如时间、地理位置、业务线等)将数据分散到多个不同的索引中的方法。这种做法可以提高Elasticsearch的性能和可管理性,尤其是在处理大量数…

不到1s生成mesh! 高效文生3D框架AToM

论文题目: AToM: Amortized Text-to-Mesh using 2D Diffusion 论文链接: https://arxiv.org/abs/2402.00867 项目主页: AToM: Amortized Text-to-Mesh using 2D Diffusion 随着AIGC的爆火,生成式人工智能在3D领域也实现了非常显著…

NOR FLASH与NAND FLASH的详细区别

Flash 是常见的用于存储数据的半导体器件,它具有容量大、可重复擦写、按“扇区/块”擦除、掉电后数据可继续保存的特性。常见的Flash 主要有NOR Flash 和Nand Flash 两种类型,它们的特性如表 37.1.2.1.1 所示。NOR 和 NAND 是两种数字门电路,…

信钰证券:2024年最新创业板开通条件?

创业板是深圳证券买卖所建立的一个专门为创新型、成长型企业服务的板块,受到了不少投资者的关注。对于2024年最新创业板注册条件,信钰证券下面就为我们详细介绍一下。 2024年最新创业板注册条件: 1、投资者的财物要求:投资者申请…

JavaScript基础(28)_获取元素的其他样式

其他样式操作的属性 clientWidth(只读):获取元素的"可见宽度",包括内容区和内边距(返回的是一个数字,不带px,可直接进行计算)。 clientHeight(只读):获取元素的"可见高度",包括内容区…

大数据应用对企业的价值

目录 一、大数据应用价值 1.1 大数据技术分析 1.2 原有技术场景的优化 1.2.1 数据分析优化 1.2.2 高并发数据处理 1.3 通过大数据构建新需求 1.3.1 智能推荐 1.3.2 广告系统 1.3.3 产品/流程优化 1.3.4 异常检测 1.3.5 智能管理 1.3.6 人工智能和机器学习 二、大数…

mac电脑安装cocoapods出错,以及安装最新版本ruby方法

macbook安装cocoapods时碰到一个报错:大概率是ruby的版本太低导致的 sudo gem install cocoapods ERROR: Error installing cocoapods: ERROR: Failed to build gem native extension. ... Could not create Makefile due to some reason, probably lack of neces…

Mountain Lake - Forest Pack

从头开始构建的50个岩石森林资源集合,充分利用了HDRP。还支持Universal 和Built-In。 支持Unity 2020.3+、高清渲染管线、通用渲染管线、标准渲染管线。导入包后,按照README中的说明进行操作。 Mountain Lake - Rock & Tree Pack是一个由50个准备好的资源组成的集合,从头…

如何运行心理学知识(心流)来指导工作和生活

如何运用心流来指导工作和生活 如何联系我 作者:鲁伟林 邮箱:thinking_fioa163.com或vlinyes163.com GitHub:https://github.com/thinkingfioa/ReadingSummary 版权声明:文章和记录为个人所有,如果转载或个人学习…

提高网站访问速度 nginx 常用配置参数

Nginx是一种高性能的HTTP和反向代理服务器,因其轻量级、高并发处理能力和易于配置而广受欢迎。要提高网站访问速度,可以通过优化Nginx配置来实现。以下是一些可以用来提高网站访问速度的Nginx配置参数,以及它们的详细说明: …

命令行参数、环境变量

1. 命令行参数 大家平时在写主函数时基本是无参的,但其实是有参数的,先介绍前两个参数。 int main(int argc, char* argv[])第二个参数是指针数组,第一个参数是该数组的个数,我们先来写 一段代码来看看指针数组里面是什么。 1 #…

Vue3父子组件传参

一,父子组件传参: 应用场景:父子组件传参 Vue3碎片:defineEmits,defineProps,ref,reactive,onMounted 1.父组件传子组件 a.父组件传参子组件 import { ref} from vue import OnChi…

【力扣】快乐数,哈希集合+快慢指针+数学

快乐数原题地址 方法一:哈希集合 定义函数getNext(n),返回n的所有位的平方和。一直执行ngetNext(n),最终只有2种可能: n停留在1。无限循环且不为1。 证明:情况1是存在的,如力扣的示例一: 接…

Linux free命令教程:轻松愉快的掌握内存管理(附案例详解和注意事项)

Linux free命令介绍 free命令用于获取系统中可用的总随机存取内存量,已使用的内存量和系统中可用的交换内存量。free命令或实用程序还显示内核使用的缓冲内存⁵。 Linux free命令适用的Linux版本 free命令在所有主流的Linux发行版中都是可用的,包括但…