【JVM】Java程序运行时数据区
运行时数据区
运行时数据区是Java程序执行过程中管理的内存区域
Java 运行时数据区组成(JVM 内存结构)
Java 虚拟机(JVM)的运行时数据区由以下核心部分组成:
线程私有:程序计数器、Java虚拟机栈、本地方法栈。
线程共享:方法区、堆。
一、程序计数器
程序计数器存储当前执行的字节码指令地址。
线程私有:每个线程都有独立的程序计数器。
多线程场景下程序计数器的工作流程:
常见问题解答
Q:为什么程序计数器不会内存溢出?
A:其存储的是单个指令地址(指针),非用户数据。指针长度固定(32位系统4字节/64位8字节),且线程结束时自动释放。
Q:PC 如何影响程序流程控制?
A:分支指令直接修改 PC 值实现跳转:
0: iload_1
1: ifeq 12 // 如果值为0,PC跳转到12
4: iinc 1, -1 // 否则继续执行
...
12: return // 跳转目标
Q:调试器如何实现断点功能?
A:通过修改 PC 值实现:
- 在目标指令处插入特殊断点指令
- 当 PC 指向断点时暂停执行
- 显示当前堆栈和变量状态
二、Java虚拟机栈
Java虚拟机栈描述的是Java方法执行过程中的线程内存模型,主要作用是管理Java方法的调用过程。在当前线程中每个方法被调用的时候,JVM会同步创建一个栈帧呀入到虚拟机栈。栈帧中存储着局部变量表、操作数栈、动态链接、方法返回地址等。
栈帧组成
1. 局部变量表
-
存储内容:
-
this(实例对象的地址)
-
方法参数
-
局部变量
-
基本类型数据(
int
,boolean
等) -
对象引用(reference)
-
-
容量单位:变量槽(Slot)
-
32位类型占1个Slot(
int
,float
,reference
) -
64位类型占2个Slot(
long
,double
)索引 类型 名称 大小 示例值 0 reference this 1槽 0x00a3b1 1 int a 1槽 10 2 double b 2槽 20.5 4 reference c 1槽 0x00c4d2 5 long d 2槽 100
-
-
内存复用:Slot在作用域结束后可被复用
public void demo(int param) {int a = 10; // Slot 0: this | Slot 1: param | Slot 2: adouble b = 20.0; // Slot 3-4: b (占2个Slot)String s = "hello"; // Slot 5: s
}
2. 操作数栈
-
作用:执行字节码指令的工作区
-
深度:编译期确定(写入方法表的
max_stack
属性) -
示例代码及执行过程
以下面的 Java 代码为例,分析操作数栈在方法执行过程中的具体工作情况。
public class OperandStackExample {public static int add(int a, int b) {int c = a + b;return c;}public static void main(String[] args) {int result = add(3, 5);System.out.println(result);} }
编译后的字节码分析
add
方法编译后的部分字节码如下:public static int add(int, int);Code:0: iload_0 // 将局部变量表中第 0 个位置的 int 型变量(参数 a)压入操作数栈1: iload_1 // 将局部变量表中第 1 个位置的 int 型变量(参数 b)压入操作数栈2: iadd // 从操作数栈中弹出两个 int 型操作数,相加后将结果压入操作数栈3: istore_2 // 将操作数栈顶的 int 型结果弹出,存入局部变量表中第 2 个位置(变量 c)4: iload_2 // 将局部变量表中第 2 个位置的 int 型变量(变量 c)压入操作数栈5: ireturn // 将操作数栈顶的 int 型结果返回
操作数栈状态变化
- 执行
iload_0
指令后:将参数a
(值为 3)压入操作数栈,此时操作数栈栈顶元素为 3。 - 执行
iload_1
指令后:将参数b
(值为 5)压入操作数栈,此时操作数栈从栈顶到栈底元素依次为 5、3。 - 执行
iadd
指令后:从操作数栈中弹出 5 和 3,计算 3 + 5 = 8,将结果 8 压入操作数栈,此时操作数栈栈顶元素为 8。 - 执行
istore_2
指令后:将操作数栈顶的 8 弹出,存入局部变量表中变量c
的位置,此时操作数栈为空。 - 执行
iload_2
指令后:将局部变量表中变量c
的值 8 压入操作数栈,此时操作数栈栈顶元素为 8。 - 执行
ireturn
指令后:将操作数栈顶的 8 返回,方法执行结束。
- 执行
3. 动态链接
- 存储内容:指向方法区运行时常量池的引用
- 核心作用:将符号引用解析为直接引用
- 类方法调用:确定目标方法的入口地址
- 字段访问:定位字段在内存中的偏移量
4. 方法返回地址
- 两种返回方式:
- 正常返回:PC计数器值作为返回地址
- 异常退出:异常处理器表记录的地址
- 关键动作:
- 恢复上层方法的局部变量表
- 将操作数栈结果压回调用者栈帧
- 调整PC计数器
三、本地方法栈
本地方法栈是 JVM 为执行本地方法(Native Method)提供的内存区域。本地方法是使用非 Java 语言(如 C、C++)实现的方法,主要作用是管理本地方法的调用过程。
栈帧结构
本地方法栈的栈帧结构和 Java 虚拟机栈的栈帧类似,通常包含以下部分:
局部变量表:用于存储本地方法执行过程中的局部变量,包括基本数据类型和对象引用。
操作数栈:在本地方法执行计算时,用于存储操作数和中间结果。
动态链接:将符号引用转换为直接引用,以便在运行时能够正确调用方法。
方法返回地址:记录方法执行完毕后返回的位置。
以上都是线程不共享,每个线程私有的内存区域,与每个线程当前执行位置与内存模型息息相关,都在线程创建时创建,在线程销毁时销毁。
四、方法区
方法区存放着已经被虚拟机加载的类型信息、常量、静态变量等数据。
储存内容
-
类型信息:
- 类的全限定名(如
java.lang.String
) - 类的直接父类的全限定名(对于
Object
,没有父类) - 类的修饰符(
public
,abstract
,final
等) - 实现的接口列表
- 字段信息(字段名称、类型、修饰符)
- 方法信息(方法名称、返回类型、参数类型/数量、修饰符、字节码、操作数栈和局部变量表大小)
- 类的全限定名(如
-
运行时常量池:
- 是字节码文件中常量池的运行时表现形式,被每个类或接口所独有。
- 包含:
- 编译期已知的字面量:文本字符串、
final
常量值。 - 符号引用:类和接口的完全限定名、字段的名称和描述符、方法的名称和描述符。这些符号引用在类加载的解析阶段会被转化为直接引用(如内存地址)。
- 编译期已知的字面量:文本字符串、
JDK 7 之后,字符串常量池从方法区移到了堆中,但其他类型的常量(如整数常量、浮点常量等)依然存于运行时常量池,位于元空间。
-
静态变量:
- 静态变量存储在方法区,可供所有的实例访问。
实现演变
- 永久代(JDK7及以前):方法区使用永久代实现,永久代使用堆中的一部分内存,有固定大小限制,容易发生内存溢出。
- 元空间(JDK8以后):移除永久代,使用元空间实现方法区,元空间使用系统直接内存,不再受堆内存的限制。
五、堆
在JVM中,堆的作用是存放所有的对象实例。堆被所有的线程共享。
存储内容
1.对象实例
- 所有
new
创建的对象。 - 数组对象:
int[]
,double[]
等基本类型数组(数组对象本身及其元素值都在堆中连续空间中)。String[]
,Object[]
等引用类型数组(数组对象本身在堆中,其元素是指向堆中其他对象的引用)。
易混淆点
- 字符串对象与字符串常量池:
- 字符串对象本身(如
new String("abc")
或运行时拼接生成的String
)存储在堆中。 - 字符串常量池自 JDK 7 起移至堆中,它存储的是:
- 字符串字面量(如
"abc"
)的引用(指向堆中的String
对象)。 String.intern()
方法返回的字符串的引用。
- 字符串字面量(如
- 总结:字符串对象在堆,常量池(
StringTable
)也在堆(存储引用),但常量池本身是一个哈希表结构。
- 字符串对象本身(如
- 静态变量引用的对象:
- 静态变量(
static
修饰)的引用本身存储在方法区(JDK 7+ 的元空间)。 - 但静态变量指向的对象实例(如
static Object obj = new Object();
中的new Object()
)存储在堆中。
- 静态变量(
- **类信息:
- 类的元数据(如类名、方法字节码、字段结构等)存储在方法区(元空间),不在堆中。
- 类的
Class
对象(如String.class
)是一个特殊的对象实例,存储在堆中。
- 基本类型局部变量 vs. 成员变量:
- 成员变量(在对象内部):基本类型(如
int
,double
)的值直接存在堆内对象内存中。 - 局部变量(在方法内部):基本类型(如
int i = 10;
)的值存储在 Java 栈的栈帧的局部变量表 中,不在堆中。
- 成员变量(在对象内部):基本类型(如
相关文章:

【JVM】Java程序运行时数据区
运行时数据区 运行时数据区是Java程序执行过程中管理的内存区域 Java 运行时数据区组成(JVM 内存结构) Java 虚拟机(JVM)的运行时数据区由以下核心部分组成: 线程私有:程序计数器、Java虚拟机栈、本地方…...
NVIDIA英伟达describe-anything软件本地电脑安装部署完整教程
describe-anything是英伟达联合其他大学开发的一款图片视频内容分析总结软件,可通过AI描述任意图片视频选中区域内容,非常强大,下面是describe-anything本地电脑安装部署教程。 首先电脑上安装git https://github.com/git-for-windows/git/…...

计算机视觉入门:OpenCV与YOLO目标检测
计算机视觉入门:OpenCV与YOLO目标检测 系统化学习人工智能网站(收藏):https://www.captainbed.cn/flu 文章目录 计算机视觉入门:OpenCV与YOLO目标检测摘要引言技术原理对比1. OpenCV:传统图像处理与机器学…...
Java 中的 ThreadLocal 详解:从基础到源码
Java 中的 ThreadLocal 详解:从基础到源码 引言 在 Java 多线程编程中,ThreadLocal是一个经常被提及的概念。它提供了一种线程局部变量的机制,使得每个线程都可以独立地存储和访问自己的变量副本,而不会与其他线程产生冲突。本文…...
(二)开启深度学习动手之旅:先筑牢预备知识根基
1 数据操作 数据操作是深度学习的基础,包括数据的创建、索引、切片、运算等操作。这些操作是后续复杂模型构建和训练的前提。 入门 :理解如何使用NumPy创建数组,这是深度学习中数据存储的基本形式。掌握数组的属性(如数据类型dt…...
Spring Boot3.4.1 集成redis
Spring Boot3.4.1 集成redis 第一步 引入依赖 <!-- redis 缓存操作 --> <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId> </dependency> <!-- pool 对象池 …...

【Prometheus+Grafana实战:搭建监控系统(含告警配置)】
什么是Prometheus和Grafana? Prometheus:一款开源的监控告警工具,擅长时序数据存储和多维度查询(通过PromQL),采用Pull模型主动抓取目标指标。Grafana:数据可视化平台,支持多种数据…...
操作系统原理第9章 磁盘存储器管理 重点内容
目录 (一)外存的组织方式种类 (二)FAT 系统(计算) (三)文件存储空间的管理方式 (一)外存的组织方式种类 连续组织方式 原理:在磁盘等外存上&…...

一文速通Python并行计算:11 Python多进程编程-进程之间的数据安全传输-基于队列和管道
一文速通 Python 并行计算:11 Python 多进程编程-进程之间的数据安全传输-基于队列和管道 摘要: Python 多进程中,Queue 和 Pipe 提供进程间安全通信。Queue 依赖锁和缓冲区,保障数据原子性和有序性;Pipe 实现点对点单…...

LangChain-Tool和Agent结合智谱AI大模型应用实例2
1.Tool(工具) 定义与功能 单一功能模块:Tool是完成特定任务的独立工具,每个工具专注于一项具体的操作,例如:搜索、计算、API调用等 无决策能力:工具本身不决定何时被调用,仅在被触发时执行预设操作 输入输出明确:每个工具需明确定义输入、输出参数及格式 2.Agent(…...
HTML、XML、JSON 是什么?有什么区别?又是做什么的?
在学习前端开发或者理解互联网工作原理的过程中,我们经常会遇到三个非常重要的概念:HTML、XML 和 JSON。它们看起来有点像,但其实干的事情完全不同。 🏁 一、他们是谁?什么时候诞生的? 名称全称诞生时间谁…...
C++中IO文件输入输出知识详解和注意事项
以下内容将从文件流类体系、打开模式、文本与二进制 I/O、随机访问、错误处理、性能优化等方面,详解 C 中文件输入输出的使用要点,并配以示例。 一、文件流类体系 C 标准库提供三种文件流类型,均定义在 <fstream> 中: std…...

centos7.6阿里云镜像各个版本介绍
(水一期) Index of /centos-vault/centos/7.6.1810/isos/x86_64/ File NameFile SizeDateParent directory/--0_README.txt2.4 KB2018-12-01 21:21CentOS-7-x86_64-DVD-1810.iso4.3 GB2018-11-26 07:55CentOS-7-x86_64-DVD-1810.torrent86.0 KB2018-12-…...

InnoDB引擎逻辑存储结构及架构
简化理解版 想象 InnoDB 是一个高效运转的仓库: 核心内存区 (大脑 & 高速缓存 - 干活超快的地方) 缓冲池 Buffer Pool (最最核心!): 作用: 相当于仓库的“高频货架”。把最常用的数据(表数据、索引)从…...
KVM——CPU独占
文章目录 机器现况信息配置CPU独占(pin)启用 CPU 独占(隔离)验证 机器现况信息 [rootkvm-server ~]# virsh list --allId 名称 状态 --------------------------- CULinux-VM 关闭- ubuntu20.04 关闭- ubuntu24.04 关闭[roo…...

第4讲、Odoo 18 模块系统源码全解与架构深度剖析【modules】
引言 Odoo 是一款强大的开源企业资源规划(ERP)与客户关系管理(CRM)系统,其核心竞争力之一在于高度模块化的架构设计。模块系统不仅是 Odoo 框架的基石,更是实现功能灵活扩展与定制的关键。本文将结合 Odoo…...

pytorch简单线性回归模型
模型五步走 1、获取数据 1. 数据预处理 2.归一化 3.转换为张量 2、定义模型 3、定义损失函数和优化器 4、模型训练 5、模型评估和调优 调优方法 6、可视化(可选) 示例代码 import torch import torch.nn as nn import numpy as np import matplot…...
在 HTML 文件中添加图片的常用方法
本文详解HTML图片插入方法:1)通过<img>标签实现,必须含src和alt属性;2)路径支持绝对/相对引用;3)建议设置width/height保持比例;4)响应式方案用srcset适配不同设备…...

四、web安全-行业术语
1. 肉鸡 所谓“肉鸡”是一种很形象的比喻,比喻那些可以随意被我们控制的电脑,对方可以是WINDOWS系统,也可以是UNIX/LINUX系统,可以是普通的个人电脑,也可以是大型的服务器,我们可以象操作自己的电脑那样来…...
Kafka核心技术解析与最佳实践指南
Apache Kafka作为分布式流处理平台的核心组件,以其高吞吐、低延迟和可扩展性成为现代数据架构的基石。本文基于Kafka官方文档,深度解析其核心技术原理,并结合实践经验总结关键技巧与最佳实践。 Kafka的高性能源于其精巧的架构设计࿰…...

Unity基础学习(十二)Unity 物理系统之范围检测
目录 一、关于范围检测的主要API: 1. 盒状范围检测 Physics.OverlapBox 2. 球形范围检测 Physics.OverlapSphere 3. 胶囊范围检测 Physics.OverlapCapsule 4. 盒状检测 NonAlloc 版 5. 球形检测 NonAlloc 版 6. 胶囊检测 NonAlloc 版 二、关于API中的两个重…...

JVM 的垃圾回收机制 GC
C/C 这样的编程语言中,申请内存的时候,是需要用完了,进行手动释放的 C 申请内存 1)局部变量(不需要手动释放) 2)全局变量(不需要手动释放) 3)动态申请 malloc(通过 free 进行释放的) C 申请内存 1)局部变量 2)全局变量/静态变量 3)动态申请 new 通过 delete 进行释放 …...
TypeScript 针对 iOS 不支持 JIT 的优化策略总结
# **TypeScript 针对 iOS 不支持 JIT 的优化策略总结** 由于 iOS 的 **JavaScriptCore (JSC)** 引擎 **禁用 JIT(Just-In-Time 编译)**,JavaScript 在 iOS 上的执行性能较差,尤其是涉及动态代码时。 **TypeScript(T…...
00 QEMU源码中文注释与架构讲解
QEMU源码中文注释与架构讲解 先占坑:等后续完善后再更新此文章 注释作者将狼才鲸创建日期2025-05-30更新日期NULL CSDN阅读地址:00 QEMU源码中文注释与架构讲解Gitee源码仓库地址:才鲸嵌入式/qemu 一、前言 参考网址 QEMU 源码目录简介qe…...
ansible template 文件中如果包含{{}} 等非ansible 变量处理
在 Ansible 模板中,如果你的 Python 脚本里有大量 {}、f""、或者其他 Jinja 会误解析的语法,就需要用 {% raw %}…{% endraw %} 把它们包起来,只在需要替换变量的那一行单独“放行”。例如: {% raw %} #!/usr/bin/env …...
Screen 连接远程服务器(Ubuntu)
连接 1. 安装screen 默认预安装,可以通过命令查看: screen --version 若未安装: # Ubuntu/Debian sudo apt-get install screen 2. 本机连接远程服务器 ssh root192.168.x.x 在远程服务器中打开screen: screen -S <nam…...

路由器、网关和光猫三种设备有啥区别?
无论是家中Wi-Fi信号的覆盖,还是企业网络的高效运行,路由器、网关和光猫这些设备都扮演着不可或缺的角色。然而,对于大多数人来说,这三者的功能和区别却像一团迷雾,似懂非懂。你是否曾疑惑,为什么家里需要光…...

vscode实时预览编辑markdown
vscode实时预览编辑markdown 点击vsode界面,实现快捷键如下: 按下快捷键 CtrlShiftV(Windows/Linux)或 CommandShiftV(Mac)即可在侧边栏打开 Markdown 预览。 效果如下:...

2505软考高项第一、二批真题终极汇总
第一批2025.05综合题(75道选择题) 1、2025 年中央一号文件对进一步深化农村改革的各项任务作出全面部署。“推进农业科技力量协同攻关”的相关措施不包括()。 A.强化农业科研资源力量统筹,培育农业科技领军企业 B.发挥农业科研平台作用&…...

云原生安全基础:Linux 文件权限管理详解
🔥「炎码工坊」技术弹药已装填! 点击关注 → 解锁工业级干货【工具实测|项目避坑|源码燃烧指南】 在云原生环境中,Linux 文件权限管理是保障系统安全的核心技能之一。无论是容器化应用、微服务架构还是基础设施即代码(IaC…...