JVM基础知识(一)
1.整体架构和组件
1.Class Loader
Class Loader(类加载器)负责将.class文件加载到JVM中,并生成对应的Java类对象(Class对象)。Java中有三种类加载器:
- Bootstram ClassLoader:加载核心类库,使用C++实现,是JVM的一部分;
- Extension ClassLoader:加载Java扩展类库(例如javax.*包),使用Java实现,是sun.misc.Launcher的一部分;
- App ClassLoader:加载应用程序类,使用Java实现,是ClassLoader的子类。
.2.Execution Engine
Execution Engine(执行引擎)负责解释字节码,将其转换为机器指令,并执行程序。JVM的执行引擎包括两种模式:
- 解释器模式(Interpretive Mode):逐行解释字节码,并执行相应的机器指令。这种模式的优点是可以快速启动,但是执行速度较慢。
- 编译器模式(Compiler Mode):将字节码编译为本地机器指令,并执行编译后的代码。这种模式的优点是执行速度快,但是启动速度慢。
JVM采用了混合模式(Mixed Mode),在程序运行的过程中根据需要动态地选择使用解释器模式或编译器模式。
3.Runtime Data Area
Runtime Data Area(运行时数据区)是JVM中的数据存储区域,包括以下组件:
- Method Area(方法区):存储类信息、常量、静态变量等数据。
- Heap(堆):存储Java对象和数组。
- Stack(栈):存储Java方法的局部变量、操作数栈、方法出口等信息。
- PC Register(程序计数器):存储正在执行的Java方法的地址。
- Native Method Stack(本地方法栈):为Java调用本地方法提供支持。
4.Native Method Interface
Native Method Interface(本地方法接口)允许Java代码调用C或C++编写的本地方法。本地方法通过JNI(Java Native Interface)实现。JVM将Java参数转换为C/C++参数,调用本地方法并返回结果。
JVM的整体架构和组件是Java程序运行的基础,对于Java程序员来说,了解JVM的原理和内部机制可以帮助他们写出更高效、更稳定的Java程序。
2.组件间交互方式
2.1Class Loader和Method Area
当一个Java类第一次被加载时,Class Loader会将类的.class文件读入内存,并在Method Area中创建对应的Class对象,包括类的成员变量、方法等信息。在JVM运行期间,所有的类信息都保存在Method Area中,包括类的字节码、运行时常量池、字段和方法信息等。
2.2Heap和Stack
在Java程序中,创建对象时,它们的实例数据存储在Heap中,而对象的引用则存储在Stack中。每个Java方法都会创建一个栈帧(Stack Frame),存储该方法的局部变量、操作数栈、方法出口等信息,栈帧也存储在Stack中。
当一个Java方法被调用时,JVM会在Stack中创建一个新的栈帧,并将该栈帧推入栈顶。当方法执行完成后,JVM会弹出该栈帧,并回收其内存空间。
2.3Execution Engine和Method Area
Execution Engine负责执行Java字节码,并将其转换为计算机能够执行的机器指令。在执行字节码之前,Execution Engine需要在Method Area中查找字节码、常量等信息,并将其载入运行时常量池中。
2.4Native Method Interface和Native Method Stack
当Java程序需要调用C/C++编写的本地方法时,JVM会将Java参数转换为C/C++参数,并调用本地方法。本地方法的结果会被返回给Java程序,并且需要将C/C++结果转换为Java结果。
Native Method Interface提供了一种机制,可以在Java程序中调用C/C++编写的本地方法,使Java程序能够与底层系统交互。
3.类加载器的工作原理和类加载的过程
类加载器(ClassLoader)是JVM的一个重要组成部分,它负责将Java类从磁盘或网络等外部存储器中加载到JVM的内存中。类加载器采用的是“双亲委派模型”,即当一个类需要被加载时,它首先会委托它的父类加载器寻找该类,直到最终委托到启动类加载器为止。如果所有的父类加载器都无法找到该类,则由该类加载器自行加载。
类加载的过程通常包括以下三个阶段:
-
加载(Loading):查找并加载类的二进制数据。类加载器首先会通过类的全限定名找到对应的.class文件,然后将二进制数据读入内存,并在内存中创建对应的Class对象。需要注意的是,同一个类在JVM中只会被加载一次。
-
连接(Linking):将类的二进制数据合并到JVM的运行时环境中。连接阶段包括三个步骤:
- 验证(Verification):确保类的二进制数据符合JVM规范,并且没有安全漏洞。
- 准备(Preparation):为类的静态变量分配内存,并设置默认值。
- 解析(Resolution):将符号引用替换为直接引用,即将类、字段、方法等引用转换为内存地址。
- 初始化(Initialization):为类的静态变量赋初值,并执行类的静态代码块。在JVM中,类的初始化是一个线程安全的操作,保证了类只会被初始化一次。如果该类还有父类,那么会先初始化父类。
需要注意的是,JVM只有在需要用到某个类时才会进行类的加载和初始化,这种机制被称为“延迟加载”。同时,JVM还支持动态类加载机制,可以在程序运行期间通过Java反射机制加载新的类,并将其加入到JVM中。
4.字节码指令集的基本语法和用法
Java代码在经过编译器编译后,会被转换成字节码(Bytecode),也就是一种跨平台的中间代码。字节码指令集是Java虚拟机(JVM)可以识别并执行的代码格式。字节码指令集具有简洁、紧凑的特点,并且与底层的硬件架构无关,因此可以在不同的平台上运行。
字节码指令集由单个字节的指令组成,每个指令都有一个操作码(Opcode)和一个或多个操作数。Java虚拟机通过执行一系列的字节码指令来完成Java程序的运行。
下面是字节码指令集的一些基本语法和用法:
4.1加载和存储指令
- 从局部变量表加载值到操作数栈:iload, dload, aload, etc.
- 从操作数栈存储值到局部变量表:istore, dstore, astore, etc.
4.2运算指令
- 二进制运算指令:iadd, dadd, isub, dsub, imul, dmul, idiv, ddiv, irem, drem, etc.
- 位运算指令:ishl, ishr, iushr, iand, ior, ixor, etc.
4.3类型转换指令
- 将整型值转换为其他类型:i2d, i2l, i2f, etc.
- 将浮点型值转换为其他类型:d2i, d2l, d2f, etc.
- 将长整型值转换为其他类型:l2i, l2d, l2f, etc.
4.4控制指令
- 条件跳转指令:ifeq, ifne, iflt, ifgt, ifle, ifge, etc.
- 无条件跳转指令:goto, goto_w, etc.
- 返回指令:ireturn, dreturn, areturn, etc.
4.5对象操作指令
- 创建新对象指令:new, newarray, anewarray, etc.
- 字段操作指令:getfield, putfield, getstatic, putstatic, etc.
- 方法调用指令:invokevirtual, invokespecial, invokestatic, invokeinterface, etc.
总的来说,字节码指令集提供了Java虚拟机执行Java程序的基本语法和用法,同时也是Java程序跨平台运行的重要保障之一。
5.JIT编译器和AOT编译器
JIT编译器和AOT编译器都是将代码转换为机器码的工具,但它们的工作方式和优缺点存在较大差异。
JIT编译器(Just-In-Time Compiler)在程序运行过程中,将字节码实时编译为本地机器码执行。JIT编译器可以根据程序的实际运行情况,对热点代码进行优化,提高程序的执行效率。JIT编译器的优点包括:
- 即时编译,避免了预编译导致的启动时间过长问题;
- 动态编译,可以根据程序的实际运行情况进行优化,提高程序的执行效率;
- 与Java虚拟机紧密结合,提高了程序的可移植性和兼容性。
JIT编译器的缺点包括:
- 编译时间较长,可能会影响程序的响应时间;
- 对于一些只执行一次的代码,JIT编译器不会进行优化,浪费了一些性能资源;
- JIT编译器会占用较多的内存空间。
AOT编译器(Ahead-Of-Time Compiler)在程序运行前,将Java字节码编译为本地机器码,生成可执行文件。AOT编译器可以通过静态编译的方式,对整个程序进行优化,提高程序的执行效率。AOT编译器的优点包括:
- 编译时间较短,启动时间较短;
- 可以进行全局优化,对整个程序进行优化,提高程序的执行效率;
- 可以在没有Java虚拟机的环境下运行程序。
AOT编译器的缺点包括:
- 缺乏动态优化,对于程序的实际运行情况无法进行优化;
- 可能导致可移植性和兼容性问题;
- 占用磁盘空间较大,难以适用于资源受限的环境。
综上所述,JIT编译器和AOT编译器在实现方式和优缺点上存在差异,各自适用于不同的场景。在Java虚拟机中,JIT编译器是主流的编译器,可以提供动态优化和更好的可移植性;而AOT编译器则更适用于一些特定场景,如嵌入式系统或移动端应用。
相关文章:
JVM基础知识(一)
1.整体架构和组件 1.Class Loader Class Loader(类加载器)负责将.class文件加载到JVM中,并生成对应的Java类对象(Class对象)。Java中有三种类加载器: Bootstram ClassLoader:加载核心类库&…...
ASP.NET Core Web API用户身份验证
一、JWT介绍 ASP.NET Core Web API用户身份验证的方法有很多,本文只介绍JWT方法。JWT实现了服务端无状态,在分布式服务、会话一致性、单点登录等方面凸显优势,不占用服务端资源。简单来说,JWT的验证过程如下所示: &a…...
785. 快速排序
785. 快速排序 给定你一个长度为 n n n 的整数数列。 请你使用快速排序对这个数列按照从小到大进行排序。 并将排好序的数列按顺序输出。 输入格式 输入共两行,第一行包含整数 n n n。 第二行包含 n n n 个整数(所有整数均在 1 ∼ 1 0 9 1 \th…...
C6678学习-IPC
文章目录 1、简介2、模块MultiProc静态设置(cfg设置)动态设置 IPCNotifyMessageQShareRegion 1、简介 IPC: Inter-Processor Communication 处理器间通信,指提供多处理器环境中的处理器之间的通信、相同处理器不同线程间的通信。包括数据传递…...
利用 Delte-Sigma ADC简化电路设计
很多时候在电路中选择合适的 ADC可以很大程度上简化前端的电路。这里我们一起来看一个电阻电桥的例子: 这里用到了一只仪表放大器和一只运算放大器,他们实际上主要完成了三个功能: 1. 抑制了 2.5V的共模信号; 2. 将-1…...
如何在 Windows 11 启用 Hyper-V
准备在本机玩一下k8s,需要先启用 Hyper-V,谁知道这一打开,没有 Hyper-V选项: 1、查看功能截图: 2、以下文件保存记事本,然后重命名为*.bat pushd "%~dp0" dir /b %SystemRoot%\servicing\Packa…...
哈希表企业应用-DNA的字符串检测
DNA的字符串检测-引言 若干年后, ikun DNA 检测部成立,专门对 这些ikun的解析检测 突然发现已经完全控制不了 因为学生已经会了 而且是太会了 所以DNA采用 以下视频测试: ikun必进曲 ikun必经曲 ikun必阶曲 如何感受到了吧!,如果你现在唱跳并且还Rap 还有打篮球 还有铁山靠 那…...
Kafka运维与监控
Kafka运维与监控 Kafka运维与监控一、简介二、运维1.安装和部署安装部署 2.优化参数配置配置文件高级配置分区和副本设置分区数量设置副本数量设置 网络参数调优传输机制设置连接数和缓冲区大小设置 消息压缩和传输设置消息压缩设置消息传输设置 磁盘设置和文件系统分区磁盘容量…...
【Redis—哨兵机制】
文章目录 概念哨兵机制如何工作的监控(如何判断主节点真的故障了)哪个哨兵进行主从故障转移?故障转移流程哨兵集群 概念 当进行主从复制时,如果主节点挂掉了,那么没有主节点来服务客户端的写操作请求了,也…...
MySQL学习笔记第七天
第07章单行函数 2. 数值函数 2.4 指数函数、对数函数 函数用法POW(x,y),POWER(X,Y)返回x的y次方EXP(X)返回e的x次方,其中e是一个常数,2.718281828459045LN(X),LOG(X)返回以e为底的X的对数,当x<0时,返…...
中级软件设计师备考---程序设计语言和法律法规知识
目录 需要掌握的程序语言特点法律法规知识---保护期限法律法规知识---知识产权人确定法律法规知识---侵权判定标准化基础知识 需要掌握的程序语言特点 Fortran语言:科学计算、执行效率高Pascal语言:为教学而开发的、表达能力强,演化出了Delp…...
Leetcode434. 字符串中的单词数
Every day a leetcode 题目来源:434. 字符串中的单词数 解法1:istringstream 我们知道,C默认通过空格(或回车)来分割字符串输入,即区分不同的字符串输入。 istringstream类用于执行C风格的串流的输入操…...
C++ cmake工程引入qt6和Quick 教程
目录标题 前言QML简介锻炼C水平 cmake修改方法方式一(qt6_add_resources)方式二 (qt_add_qml_module ) 其他相关知识为什么会有_other_files?qt_standard_project_setup() 函数qt_add_qml_module() 和 qt6_add_resources()的方式差异const QU…...
JavaEE - 网络编程
一、网络编程基础 为什么需要网络编程? 用户在浏览器中,打开在线视频网站,如优酷看视频,实质是通过网络,获取到网络上的一个视频资源。 与本地打开视频文件类似,只是视频文件这个资源的来源是网络。 相比本…...
【Android车载系列】第11章 系统服务-SystemServer自定义服务
1 编写自定义系统服务 1.1 AIDL接口定义 系统源码目录/frameworks/base/core/java/android/app/下新建AIDL接口IYvanManager.aidl package android.app;/** * 目录:/frameworks/base/core/java/android/app/IYvanManager.aidl */ interface IYvanManager{String …...
Lerna
Lerna Lerna是一个优化基于gitnpm的多pagkage项目的管理工具 解决的痛点 痛点一:重复操作 多Package本地link多Package依赖安装多Package单元测试多Package代码提交多Package代码发布 痛点二:版本一致性 发布时版本一 致性发布后相互依赖版本升级 package越多,管…...
迁移学习 pytorch
迁移学习(Transfer Learning)是通过使用一个预训练模型来快速训练一个新的网络模型,通常应用于数据集较小或计算资源较少的情况下。在 PyTorch 中,由于 torchvision 库中已经内置了一些经典的预训练模型,因此我们可以通过简单的调用函数来实现迁移学习。 下面是一个基于 …...
【python】keras包:深度学习( RNN循环神经网络 Recurrent Neural Networks)
RNN循环神经网络 应用: 物体移动位置预测、股价预测、序列文本生成、语言翻译、从语句中自动识别人名、 问题总结 这类问题,都需要通过历史数据,对未来数据进行预判 序列模型 两大特点 输入(输出)元素具有顺序关系…...
vue框架快速入门
vue 1、第一个Vue程序1.1、什么是Vue程序1.2、为什么要使用MVVM1.3、Vue1.4、第一个vue程序 2、基础语法2.1、v-bind2.2、v-if, v-else2.3、v-for2.4、v-on 3、Vue表单双绑、组件3.1、什么是双向数据绑定3.2、在表单中使用双向数据绑定3.3、什么是组件 4、Axios异步…...
Java连接顺丰开放平台
今天使用Java去访问顺丰的开放平台时,JSON转换一直不成功,最终发现是 可以看到这里是 "apiResultData": "{\"success\": .........它是以 " 开头的!!!如果是对象的话,那么…...
前端三剑客 - HTML
前言 前面都是一些基础的铺垫,现在就正式进入到web开发环节了。 我们的目标就是通过学习 JavaEE初阶,搭建出一个网站出来。 一个网站分成两个部分: 前端(客户端) 后端(服务器) 通常这里的客户端…...
【计算机视觉 | 自然语言处理】BLIP:统一视觉—语言理解和生成任务(论文讲解)
文章目录 一、前言二、试玩效果三、研究背景四、模型结构五、Pre-training objectives六、CapFilt架构七、Experiment八、结论 一、前言 今天我们要介绍的论文是 BLIP,论文全名为 Bootstrapping Language-Image Pre-training for Unified Vision-Language Understa…...
c++基础-运算符
目录 1关系运算符 2运算符优先级 3关系表达式的书写 代码实例: 下面是面试中可能遇到的问题: 1关系运算符 C中有6个关系运算符,用于比较两个值的大小关系,它们分别是: 运算符描述等于!不等于<小于>大于<…...
美术馆c++
题目: 杜老师非常喜欢玩一种叫做“美术馆”的数字游戏,蜗蜗看了之后决定也来试一试,他改编了这个游戏,规则如下: 有一个 n� 行 m� 列的方格,每一个格子中有一个数,数字…...
浅谈MySQL索引以及执行计划
MySQL索引及执行计划 🐪索引的作用🐫索引的分类(算法)🦙BTREE索引算法演变🦒Btree索引功能上的分类4.1 辅助索引4.2 聚集索引4.3 辅助索引和聚集索引的区别 🐘辅助索引分类🦏索引树高…...
在c++项目中使用rapidjson(有具体的步骤,十分详细) windows10系统
具体的步骤: 先下载rapidjson的依赖包 方式1:直接使用git去下载 地址:git clone https://github.com/miloyip/rapidjson.git 方式2:下载我上传的依赖包 将依赖包引入到项目中 1 将解压后的文件放在你c项目中 2 将rapidjson文…...
编译方式汇总:Makefile\configure\autogen.sh\configure.ac、Makefile.am文件
一、前言 文章目的:针对各种开源项目,由于部分项目文档写的不够详细,(或者是我太菜了),没有进行详细的介绍怎么编译该项目,导致花费过多时间在查找如何编译该项目上。因此该篇文章针对目前遇到的…...
explicit关键字
explicit关键字只能用来修饰构造函数。使用explicit可以禁止编译器自动调用拷贝初始化,还可以禁止编译器对拷贝函数的参数进行隐式转换。 那么什么是隐式转换呢? 类 命名 参数; //有参构造类 命名 命名对象; //拷贝构造&#x…...
[优雅的面试] 你了解python的对象吗
前情提要:小编面试,结果面试官着急去吃饭~又约了这次来面,不晓得又会问什么问题呢? 面试官大佬:小伙子来的挺准时的(赞赏的表情~),今天咱们接着聊哈,小伙子,你有对象了没?…...
【hello Linux】线程概念
目录 1. 线程概念的铺设 2. Linux线程概念 2.1 什么是线程 2.2 线程的优点 2.3 线程的缺点 2.4 线程异常 2.5 线程用途 3. Linux进程VS线程 4. Linux线程控制 4.1 POSIX线程库 4.2 创建线程 4.3 进程ID和线程ID 4.4 线程终止 4.5 线程等待 4.6 分离线程 Linux🌷 1…...
wordpress搜索小工具/lol今日赛事直播
需求:点击某个标签,紧随其后的ul列表展开或者关闭并有transition效果。 难点:ul 里面的 li 数量未知,ul 高度不定,需要获取 li 数量乘以 li 高度然后计算出 ul 高度。 直接上代码: // 属性型指令࿰…...
深圳龙岗疫情最新消息今天又封了/seo站内优化和站外优化
今天在用一键安装mysql的shell脚本安装mysql-5.1.73软件后发现mysql始终无法启动,多次执行后依旧报错,只能去查看error日志,发现了如下的2个错误: 错误一:Fatal error: Cant open and lock privilege tables: Table my…...
华为网站建站/网上代写文章一般多少钱
之前编译的参数没有添加mysqli支持,因代码需要,必须添加上去。这次尝试一下扩展编译。 由于是源代码安装的,所以在php的目录bin下面有相关的命令。 到解压的源代码的ext目录下面,进入mysqli目录,执行/home/php/bin/php…...
买汽车最好的网站建设/百度域名注册查询
很久没写过技术类文章,懒了,今天同事分享了一份超时相关问题的解决办法,我记录到博客上,以备日后所需。多谢龚同学的分享。在做项目中,遇到比较多的超时问题跟大家分享下,具体超时时间设置多少可以根据监控数据、应用容…...
知名网络公司有哪些/济宁seo推广
先打出nand表0 nand 011 nand 100 nand 111 nand 01容易发现(!a)a nand a然后(a&b)!(a nand b)然后(a|b)!((!a)&(!b))然后(a^b)(a|b)&(a nand b)所以通过nand我们可以实现任意一种位运算所以每一位我们想得到0/1都是可以的按道理[L,R]中符合位数要求的数都能得到然…...
互联网网站建设哪里好/全国各城市疫情搜索高峰进度
在科普今天的知识前,不禁让小编回忆起大学校园的美好时光,那个时候小编还是个走在绿树荫下的青涩少年啊,在一次参加关于肿瘤免疫学的学术会议上,看到了类似下面这种图,我就在想,这小鼠是修炼了什么内家功法…...