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方法(使用其他语言编写的代码)。
相关文章:
JVM体系
JVM是一种虚拟的计算机,它模拟了一个完整的硬件系统,并运行在一个完全隔离的环境中。这意味着JVM可以看作是一个在操作系统之上的计算机系统,与VMware、Virtual Box等虚拟机类似。JVM的设计目标是提供一个安全、可靠、高效且跨平台的运行环境…...
.NET命令行(CLI)常用命令
本文用于记录了.NET软件开发全生命周期各阶段常用的一些CLI命令,用于开发速查。 .NET命令行(CLI)常用命令 项目创建(1)查看本机SDK(2)查看本机可以使用的.NET版本(3)生成…...
六、Redis之数据持久化及高频面试题
6.1 数据持久化 官网文档地址:https://redis.io/docs/manual/persistence/ Redis提供了主要提供了 2 种不同形式的持久化方式: RDB(Redis数据库):RDB 持久性以指定的时间间隔执行数据集的时间点快照。AOF࿰…...
爬虫——ajax和selenuim总结
为什么要写这个博客呢,这个代码前面其实都有,就是结束了。明天搞个qq登录,这个就结束了。 当然也会更新小说爬取,和百度翻译,百度小姐姐的爬取,的对比爬取。总结嘛!!!加…...
【Python】单元测试unittest框架
note 使用unittest框架进行单元测试是Python标准库的一部分,提供了编写测试用例、测试套件以及运行测试的能力。测试用例是继承自unittest.TestCase的类。在这个类中,你可以定义一系列的方法来测试不同的行为。每个测试方法都应该以test开头。 文章目录…...
(三十七)大数据实战——Solr服务的部署安装
前言 Solr是一个基于Apache Lucene的开源搜索平台,它提供了强大的全文搜索、分布式搜索和数据分析功能。Solr 可以用于构建高性能的搜索应用程序,支持从海量数据中快速检索和分析信息。Solr 使用倒排索引和先进的搜索算法,可实现快速而准确的…...
在Ubuntu22.04上部署FoooCUS2.1
Fooocus 是一款基于 Gradio的图像生成软件,Fooocus 是对 Stable Diffusion 和 Midjourney 设计的重新思考: 1、从 Stable Diffusion 学习,该软件是离线的、开源的和免费的。 2、从 Midjourney 中学到,不需要手动调整,…...
详解C语言中的野指针和assert断言
目录 1.野指针1.1 野指针成因1.1.1 指针未初始化1.1.2 指针越界访问1.1.3 指针指向的空间释放 1.2 如何规避野指针1.2.1 指针初始化1.2.2 小心指针越界1.2.3 指针变量不再使用时,及时置为NULL,指针使用之前检查1.2.4 避免返回局部变量的地址 2.assert断言…...
Vue源码系列讲解——模板编译篇【四】(文本解析器)
1. 前言 在上篇文章中我们说了,当HTML解析器解析到文本内容时会调用4个钩子函数中的chars函数来创建文本型的AST节点,并且也说了在chars函数中会根据文本内容是否包含变量再细分为创建含有变量的AST节点和不包含变量的AST节点,如下ÿ…...
微信小程序开发学习笔记《17》uni-app框架-tabBar
微信小程序开发学习笔记《17》uni-app框架-tabBar 博主正在学习微信小程序开发,希望记录自己学习过程同时与广大网友共同学习讨论。建议仔细阅读uni-app对应官方文档 一、创建tabBar分支 运行如下的命令,基于master分支在本地创建tabBar子分支&#x…...
《区块链公链数据分析简易速速上手小册》第5章:高级数据分析技术(2024 最新版)
文章目录 5.1 跨链交易分析5.1.1 基础知识5.1.2 重点案例:分析以太坊到 BSC 的跨链交易理论步骤和工具准备Python 代码示例构思步骤1: 设置环境和获取合约信息步骤2: 分析以太坊上的锁定交易步骤3: 跟踪BSC上的铸币交易 结论 5.1.3 拓展案例 1:使用 Pyth…...
【芯片设计- RTL 数字逻辑设计入门 15 -- 函数实现数据大小端转换】
文章目录 函数实现数据大小端转换函数语法函数使用的规则Verilog and Testbench综合图VCS 仿真波形 函数实现数据大小端转换 在数字芯片设计中,经常把实现特定功能的模块编写成函数,在需要的时候再在主模块中调用,以提高代码的复用性和提高设…...
Codeforces Round 925 (Div. 3) D. Divisible Pairs (Java)
Codeforces Round 925 (Div. 3) D. Divisible Pairs (Java) 比赛链接:Codeforces Round 925 (Div. 3) D题传送门:D.Divisible Pairs 题目:D.Divisible Pairs 题目描述 输出格式 For each test case, output a single integer — the num…...
【C语言】实现单链表
目录 (一)头文件 (二)功能实现 (1)打印单链表 (2)头插与头删 (3)尾插与尾删 (4) 删除指定位置节点 和 删除指定位置之后的节点 …...
Hive调优——合并小文件
目录 一、小文件产生的原因 二、小文件的危害 三、小文件的解决方案 3.1 小文件的预防 3.1.1 减少Map数量 3.1.2 减少Reduce的数量 3.2 已存在的小文件合并 3.2.1 方式一:insert overwrite (推荐) 3.2.2 方式二:concatenate 3.2.3 方式三ÿ…...
设计模式(行为型模式)责任链模式
目录 一、简介二、责任链模式2.1、处理器接口2.2、具体处理器类2.3、使用 三、优点与缺点 一、简介 责任链模式(Chain of Responsibility Pattern)是一种行为设计模式,允许你将请求沿着处理者链进行传递,直到有一个处理者能够处理…...
HTTP和HTTPS区别!
http 是我们几乎天天都要打交道的东西,相关知识点有点多,所以也有不少面试必问的点,这里做了一些整理,帮且大家树立完整的 http 知识体系,对面试官说 so easy HTTP 的特点和缺点 特点:无连接、无状态、灵…...
麻将普通胡牌算法(带混)
最近在玩腾讯的麻将游戏,但是经常需要充值,于是就想自己实现一个简单的单机麻将游戏.第一个难点就是实现胡牌的判断.这里写一下心得. 术语 本文的胡牌是指手牌构成了3N2的牌型,即一对做将,剩下的牌均为刻子(3张一样的牌)或者顺子(3张连续的牌比如234饼). 下面就是一个14张牌…...
Rust结构体详解:定义、使用及方法
Rust 是一门强调安全性和性能的系统级编程语言,它引入了结构体(struct)作为一种自定义的数据类型,允许程序员以更加灵活的方式组织和操作数据。在本篇博客中,我们将深入探讨 Rust 结构体的定义、使用以及相关概念。 什…...
LeetCode、435. 无重叠区间【中等,贪心 区间问题】
文章目录 前言LeetCode、435. 无重叠区间【中等,贪心 区间问题】题目链接及分类思路贪心、区间问题 资料获取 前言 博主介绍:✌目前全网粉丝2W,csdn博客专家、Java领域优质创作者,博客之星、阿里云平台优质作者、专注于Java后端技…...
铭豹扩展坞 USB转网口 突然无法识别解决方法
当 USB 转网口扩展坞在一台笔记本上无法识别,但在其他电脑上正常工作时,问题通常出在笔记本自身或其与扩展坞的兼容性上。以下是系统化的定位思路和排查步骤,帮助你快速找到故障原因: 背景: 一个M-pard(铭豹)扩展坞的网卡突然无法识别了,扩展出来的三个USB接口正常。…...
OpenLayers 可视化之热力图
注:当前使用的是 ol 5.3.0 版本,天地图使用的key请到天地图官网申请,并替换为自己的key 热力图(Heatmap)又叫热点图,是一种通过特殊高亮显示事物密度分布、变化趋势的数据可视化技术。采用颜色的深浅来显示…...
label-studio的使用教程(导入本地路径)
文章目录 1. 准备环境2. 脚本启动2.1 Windows2.2 Linux 3. 安装label-studio机器学习后端3.1 pip安装(推荐)3.2 GitHub仓库安装 4. 后端配置4.1 yolo环境4.2 引入后端模型4.3 修改脚本4.4 启动后端 5. 标注工程5.1 创建工程5.2 配置图片路径5.3 配置工程类型标签5.4 配置模型5.…...
3.3.1_1 检错编码(奇偶校验码)
从这节课开始,我们会探讨数据链路层的差错控制功能,差错控制功能的主要目标是要发现并且解决一个帧内部的位错误,我们需要使用特殊的编码技术去发现帧内部的位错误,当我们发现位错误之后,通常来说有两种解决方案。第一…...
pam_env.so模块配置解析
在PAM(Pluggable Authentication Modules)配置中, /etc/pam.d/su 文件相关配置含义如下: 配置解析 auth required pam_env.so1. 字段分解 字段值说明模块类型auth认证类模块,负责验证用户身份&am…...
多模态商品数据接口:融合图像、语音与文字的下一代商品详情体验
一、多模态商品数据接口的技术架构 (一)多模态数据融合引擎 跨模态语义对齐 通过Transformer架构实现图像、语音、文字的语义关联。例如,当用户上传一张“蓝色连衣裙”的图片时,接口可自动提取图像中的颜色(RGB值&…...
Nginx server_name 配置说明
Nginx 是一个高性能的反向代理和负载均衡服务器,其核心配置之一是 server 块中的 server_name 指令。server_name 决定了 Nginx 如何根据客户端请求的 Host 头匹配对应的虚拟主机(Virtual Host)。 1. 简介 Nginx 使用 server_name 指令来确定…...
深入解析C++中的extern关键字:跨文件共享变量与函数的终极指南
🚀 C extern 关键字深度解析:跨文件编程的终极指南 📅 更新时间:2025年6月5日 🏷️ 标签:C | extern关键字 | 多文件编程 | 链接与声明 | 现代C 文章目录 前言🔥一、extern 是什么?&…...
RNN避坑指南:从数学推导到LSTM/GRU工业级部署实战流程
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文全面剖析RNN核心原理,深入讲解梯度消失/爆炸问题,并通过LSTM/GRU结构实现解决方案,提供时间序列预测和文本生成…...
.Net Framework 4/C# 关键字(非常用,持续更新...)
一、is 关键字 is 关键字用于检查对象是否于给定类型兼容,如果兼容将返回 true,如果不兼容则返回 false,在进行类型转换前,可以先使用 is 关键字判断对象是否与指定类型兼容,如果兼容才进行转换,这样的转换是安全的。 例如有:首先创建一个字符串对象,然后将字符串对象隐…...
