每日面试题11:JVM

深入理解JVM:Java的“心脏”如何驱动程序运行?

为什么需要JVM?

你是否想过,为什么用Java写的程序,能在Windows、Linux、macOS上“无缝运行”?为什么开发者无需为不同操作系统重写代码?这背后的核心功臣,正是Java虚拟机(Java Virtual Machine,JVM)。

JVM是Java生态的“基石”,它不仅实现了“一次编写,随处运行”的跨平台特性,还通过内存管理、垃圾回收等机制,让开发者从繁琐的系统底层操作中解放出来,专注于业务逻辑。今天,我们就从JVM的核心架构出发,了解什么是JVM。

l


一、JVM的本质:字节码的“翻译官”与资源管家

1.1 JVM的核心职责

JVM本质上是一个​​虚拟计算机​​,它通过以下机制支撑Java程序的运行:

  • ​执行字节码​​:将Java源码编译后的.class字节码文件,翻译为具体操作系统能识别的机器码。
  • ​内存管理​​:自动分配对象内存、回收无用内存(垃圾回收),避免手动内存操作(如C++的new/delete)带来的内存泄漏或越界问题。
  • ​跨平台支持​​:通过不同平台的JVM实现(如Windows版、Linux版JVM),屏蔽底层系统差异,实现“一次编译,到处运行”。

1.2 Java代码的执行全流程

理解JVM的作用,需先看Java代码的“生命周期”:

// 示例Java代码
public class HelloJVM {public static void main(String[] args) {System.out.println("Hello, JVM!");}
}

​步骤1:编译为字节码​
通过javac HelloJVM.java命令,将Java源码编译为.class字节码文件(二进制格式,与平台无关)。

​步骤2:JVM加载并执行字节码​
JVM读取.class文件,将其翻译为对应操作系统的机器码,最终由CPU执行。

​关键优势​​:无论目标系统是Windows还是Linux,只需安装对应版本的JVM,同一个.class文件就能运行——这就是“跨平台”的本质。


二、JVM的核心架构:运行时数据区(内存结构)

JVM的内存结构是其核心组件之一,用于存储程序运行时的各类数据。根据功能不同,可分为五大区域(JDK8后部分区域名称调整):

2.1 程序计数器(Program Counter Register)

  • ​定位​​:线程私有(每个线程独立一份)。
  • ​功能​​:记录当前线程执行的​​字节码指令地址​​(类似“执行指针”)。
  • ​特点​​:
    • 若执行的是Java方法,计数器存储当前字节码的行号;若执行的是本地(Native)方法(如C/C++实现的方法),计数器值为Undefined
    • 唯一不会发生OutOfMemoryError(OOM)的区域。

​类比​​:就像阅读时做的“书签”,记录当前读到哪一页,下次继续从这里开始。

2.2 虚拟机栈(Java Virtual Machine Stack)

  • ​定位​​:线程私有(每个线程独立栈空间)。
  • ​功能​​:存储​​方法调用的局部变量、操作数栈、动态链接、方法返回地址​​等信息。
  • ​结构​​:
    每个方法调用会创建一个“栈帧”(Stack Frame),包含:
    • ​局部变量表​​:存储方法参数、局部变量(基本类型直接存值,引用类型存对象地址)。
    • ​操作数栈​​:方法执行时的临时计算空间(如a + b会将a、b压栈,计算后弹出结果)。
    • ​动态链接​​:指向方法区(元空间)中该方法的符号引用(运行时解析为直接引用)。
  • ​常见问题​​:
    • ​栈溢出(StackOverflowError)​​:栈深度超过限制(如递归调用过深)。
    • ​OOM(OutOfMemoryError)​​:栈空间扩展失败(如不断创建线程导致栈总空间耗尽)。

​示例​​:调用methodA()时,栈中会压入methodA的栈帧;若methodA调用methodB(),则继续压入methodB的栈帧,执行完methodB后弹出其栈帧,回到methodA

2.3 堆(Heap)

  • ​定位​​:线程共享(所有线程可访问同一堆空间)。
  • ​功能​​:存储​​对象实例、数组​​等几乎所有对象(除基本类型变量和对象引用外)。
  • ​特点​​:
    • 是JVM内存管理的核心区域,也是垃圾回收(GC)的主要目标区域。
    • 堆内存不足时会抛出OutOfMemoryError: Java heap space
  • ​分代设计(JDK8前)​​:
    为优化GC效率,堆通常分为​​新生代(Young Generation)​​和​​老年代(Old Generation)​​:
    • 新生代:存放生命周期短的对象(如局部变量),通过Minor GC(小范围回收)快速清理。
    • 老年代:存放生命周期长的对象(如全局缓存),通过Major GC/Full GC(大范围回收)清理。

​注意​​:JDK8后,永久代(PermGen)被元空间(Metaspace)取代,但堆的核心地位未变。

2.4 元空间(Metaspace)

  • ​定位​​:线程共享(存储类级别的元数据)。
  • ​功能​​:替代JDK7及之前的“永久代(PermGen)”,存储​​类的元信息​​(如类名、方法定义、字段信息、常量池、静态变量等)。
  • ​特点​​:
    • 不再使用JVM堆内存,而是直接使用​​本地内存​​(操作系统内存),避免了永久代的内存溢出问题。
    • 常见OOM场景:类元数据占用过多内存(如动态生成大量类,Spring框架的CGLIB代理可能触发)。

​对比永久代​​:JDK7时,字符串常量池从永久代移至堆;JDK8后,永久代完全被元空间取代。


三、JVM的其他核心组件:协同工作的“引擎”

3.1 类加载器(Class Loader)

  • ​功能​​:将.class字节码文件加载到JVM内存中,并生成对应的Class对象(程序通过Class对象访问类的方法、字段)。
  • ​加载流程​​(双亲委派模型):
    1. ​启动类加载器(Bootstrap ClassLoader)​​:加载JDK核心类(如java.lang.*),由C++实现。
    2. ​扩展类加载器(Extension ClassLoader)​​:加载jre/lib/ext目录下的扩展类。
    3. ​应用类加载器(Application ClassLoader)​​:加载用户项目中的类(如src/main/java编译后的.class文件)。
  • ​双亲委派机制​​:子加载器优先委托父加载器加载类,避免重复加载和核心类被篡改(如防止用户自定义一个java.lang.String覆盖JDK原生类)。

3.2 执行引擎(Execution Engine)

  • ​功能​​:将字节码翻译为机器码并执行。
  • ​执行方式​​:
    • ​解释执行​​:逐行读取字节码并翻译为机器码(启动快,效率低)。
    • ​即时编译(JIT, Just-In-Time)​​:对高频执行的代码(热点代码)进行批量编译,转换为机器码后缓存(长期执行效率高)。
  • ​优化技术​​:如方法内联(减少函数调用开销)、逃逸分析(判断对象是否仅在方法内使用,决定是否栈上分配)。

3.3 垃圾回收器(Garbage Collector, GC)

  • ​功能​​:自动回收堆中不再使用的对象内存,避免内存泄漏。
  • ​核心算法​​:
    • ​标记-清除(Mark-Sweep)​​:标记无用对象后清除,但会产生内存碎片。
    • ​复制算法(Copying)​​:将内存分为两块,每次只用一块,回收时复制存活对象到另一块(新生代Minor GC常用)。
    • ​标记-整理(Mark-Compact)​​:标记无用对象后,将存活对象向一端移动,避免碎片(老年代Full GC常用)。
  • ​常见收集器​​:如Serial(单线程)、Parallel(多线程)、CMS(并发标记清除,低延迟)、G1(分代收集,JDK9+默认)。

总结:JVM是Java世界的“操作系统”

JVM不仅是Java跨平台的“桥梁”,更是程序运行的“资源管家”。它的核心架构(运行时数据区、类加载器、执行引擎、GC)协同工作,确保了Java程序的高效、安全与稳定。

下次遇到StackOverflowErrorOOM时,不妨回忆一下JVM的内存结构——问题可能就出在某个区域的“超载”;而理解类加载器和GC机制,则能帮你写出更健壮、更高效的Java代码。

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

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

相关文章

Linux网络信息(含ssh服务和rsync)

73.telnet:测试端口连通性用法:telnet 主机名或IP 端口号测试目标主机的指定端口是否开放,检查网络服务连通性。eg:telnet www.baidu.com 80# 说明:# - 如果连接成功,显示 "Connected to ..."。…

【PTA数据结构 | C语言版】我爱背单词

本专栏持续输出数据结构题目集,欢迎订阅。 文章目录题目代码题目 作为一个勤奋的学生,你在阅读一段英文文章时,是否希望有个程序能自动帮你把没有背过的生词列出来?本题就请你实现这个程序。 输入格式: 输入第 1 行给…

如何使用电脑连接小米耳机(红米 redmi耳机)

如何使用电脑连接小米(红米 redmi)耳机Redmi耳机连接电脑的具体步骤如下注意事项和常见问题解决方法:Redmi耳机连接电脑的具体步骤如下 打开耳机仓盖: 首先,打开Redmi耳机的充电仓盖,但不需要取出耳机。进…

排序算法—交换排序(冒泡、快速)(动图演示)

目录 十大排序算法分类​编辑 冒泡排序 算法步骤: 动图演示: 性能分析: 代码实现(Java): 快速排序(挖坑法) 算法步骤: 动图演示: 性能分析&#xff1…

2023 年 5 月青少年软编等考 C 语言八级真题解析

目录 T1. 道路 思路分析 T2. Rainbow 的商店 思路分析 T3. 冰阔落 I 思路分析 T4. 青蛙的约会 思路分析 T1. 道路 题目链接:SOJ D1216 N N N 个以 1 ∼ N 1 \sim N 1∼N 标号的城市通过单向的道路相连,每条道路包含两个参数:道路的长度和需要为该路付的通行费(以金币的数…

【vue-4】深入理解 Vue 3 中的 v-for 指令

Vue.js 作为现代前端框架的代表之一,其模板指令系统提供了强大的数据绑定和渲染能力。其中,v-for 指令是 Vue 中最常用且最重要的指令之一,它允许我们基于数据源循环渲染元素或组件。在 Vue 3 中,v-for 保留了一贯的简洁语法&…

《R for Data Science (2e)》免费中文翻译 (第1章) --- Data visualization(1)

写在前面 本系列推文为《R for Data Science (2)》的中文翻译版本。所有内容都通过开源免费的方式上传至Github,欢迎大家参与贡献,详细信息见: Books-zh-cn 项目介绍: Books-zh-cn:开源免费的中文书籍社区 r4ds-zh-cn …

界面组件DevExpress WPF中文教程:Grid - 如何完成节点排序和移动?

DevExpress WPF拥有120个控件和库,将帮助您交付满足甚至超出企业需求的高性能业务应用程序。通过DevExpress WPF能创建有着强大互动功能的XAML基础应用程序,这些应用程序专注于当代客户的需求和构建未来新一代支持触摸的解决方案。 无论是Office办公软件…

【Prometheus+Grafana篇】监控通过Keepalived实现的MySQL HA高可用架构

💫《博主主页》:    🔎 CSDN主页__奈斯DB    🔎 IF Club社区主页__奈斯、 🔥《擅长领域》:擅长阿里云AnalyticDB for MySQL(分布式数据仓库)、Oracle、MySQL、Linux、prometheus监控;并对…

k8s:利用kubectl部署postgis:17-3.5

1.离线环境CPU:Hygon C86 7285 32-core Processor 操作系统:麒麟操作系统 containerd:1.7.27 Kubernetes:1.26.12 KubeSphere:4.1.2 kubekey:3.1.10 Harbor:2.13.1 Postgis:17-3.52.创建并执行postgresql-headless.yaml2.1创建apiVersion: v1…

Mysql(存储过程)

目录 介绍 特点 存储过程创建 系统变量(不重要) 用户变量 局部变量 if 判断 参数(in, out, inout) case while repeat loop 游标和条件处理程序-handler 存储函数 为了防止以后忘记,反复去看视频浪费时间,特写一篇 介绍 存储过程…

Effective Python 第14条: 用sort方法的key参数来表示复杂的排序逻辑

一、引言:Python排序功能的重要性 在Python开发中,排序功能是一个常见的需求。无论是处理数据、优化算法,还是提升用户体验,排序都是不可或缺的一部分。Python的列表内置了sort方法,提供了灵活的排序功能。然而&#…

react+antd 可拖拽模态框组件

DraggableModal 可拖拽模态框组件使用说明 概述 DraggableModal 是一个基于 dnd-kit/core 实现的可拖拽模态框组件,允许用户通过拖拽标题栏来移动模态框位置。该组件具有智能边界检测功能,确保模态框始终保持在可视区域内。 功能特性 ✅ 可拖拽移动&…

MySQL的基本操作及相关python代码

下面为你介绍 MySQL 的基本操作,以及对应的 Python 代码实现。我会先介绍 SQL 基本操作,再展示如何用 Python 连接 MySQL 并执行这些操作。 一、MySQL 基本操作(SQL 语句) 1. 连接数据库 bash mysql -u root -p2. 创建数据库 sql CREATE DATABASE testdb;3. 使用数据…

Armbian(斐讯N1)安装xfce桌面以及远程环境

安装xfce桌面以及vncserver(远程连接) 安装xfce桌面 apt-get install xfce4 xfce4-goodies xorg dbus-x11 x11-xserver-utils ubuntu的安装gdm3, apt install gdm3 debian安装lightdm。 apt install lightdm 安装vnc server apt-get install tightvncserver 中文字体…

【Oracle】Oracle 11g打补丁时遇到opatch apply命令无法识别

⚙️ 1. 使用完整路径执行命令 问题原因:若未将$ORACLE_HOME/OPatch加入系统PATH环境变量,直接输入opatch apply会因系统无法定位命令而报错。 解决方案: 改用绝对路径执行: $ORACLE_HOME/OPatch/opatch apply例如: /u…

单例模式详细讲解

一.定义单例模式是一种创建型设计模式,确保一个类只有一个实例,并提供一个全局访问点特点:1.构造函数和析构函数私有化2.禁用拷贝构造函数和赋值运算符重载(delete)3.利用静态成员函数和静态成员变量来给外界提供访问二…

KORGym:评估大语言模型推理能力的动态游戏平台

KORGym:评估大语言模型推理能力的动态游戏平台 现有评估基准多受领域限制或 pretraining 数据影响,难以精准测LLMs内在推理能力。KORGym平台应运而生,含50余款游戏,多维度评估,本文将深入解析其设计、框架、实验及发现…

ISPDiffuser文章翻译理解

ISPDiffuser: Learning RAW-to-sRGB Mappings with Texture-Aware Diffusion Models and Histogram-Guided Color Consistency翻译 Type: Conference paper Author: Yang Ren1,4, Hai Jiang1,4, Menglong Yang1,2,†, Wei Li1,2, Shuaicheng Liu3,4,† Select: ⭐️⭐️⭐️⭐…

C++线程池执行步骤分析,总结线程池流程

线程池流程总结:1、构造函数中创建线程,并添加到线程池(构造函数返回时,线程自动启动,并停在等待wait:从线程池取出一个任务处); 2、主线程中添加任务,到任务队列。并用“…