【JVM 03-JVM内存结构之-虚拟机栈】

虚拟机栈 笔记记录

  • 1. 定义
    • 1.1 演示栈帧
  • 2. 特点
  • 3. 线程运行诊断
    • 3.1 案例1 cpu占用过多&解决
    • 3.2 案例2 程序运行很长时间没有结果
  • 4. 拓展知识&问题辨析
    • 4.1 栈的内存越大越好嘛?(不是)
    • 4.2 方法内的局部变量是否线程安全?(是线程安全的)
      • 4.2.1 局部变量全在方法中
      • 4.2.2 局部变量可能逃离方法
    • 4.3 可能抛出的异常?
    • 4.4 什么情况下会发生栈内存溢出?
    • 4.5 如何设置栈的大小?
    • 4.6 补充栈帧的内部结构
      • 重要的两个(局部变量表&操作数栈)
        • 4.6.1 局部变量表
        • 4.6.2 操作数栈

学习资料来源-b站黑马JVM& 尚硅谷JVM精讲与GC调优

1. 定义

这里是引用

  • 虚拟机栈:线程运行需要的内存空间。栈中放的是多个栈帧。
  • 栈帧:每个方法运行时需要的内存。(比如参数,局部变量,返回地址等。)
  • 每个线程只能有1个活动栈帧,对应着当前正在执行的那个方法。
  • Java虚拟机栈(Java Virtual Machine Stack),早期也叫Java栈。每个线程在创建时都会创建一个虚拟机栈,其内部保存一个个的栈帧(Stack Frame),对应着一次次的Java方法调用。是线程私有的,生命周期和线程一致。
  • 虚拟机栈中放的一个个栈帧。
    这里是引用

1.1 演示栈帧

在这里插入图片描述

    public static void main(String[] args) {method1();}private static void method1() {method2(1,2);}private static int method2(int a, int b) {int c=a+b;return c;}

2. 特点

  • 栈是一种快速有效的分配存储方式,访问速度仅次于程序计数器。
  • 垃圾回收是否涉及栈内存?(不会,一次次方法执行后弹出栈自动被回收掉。)不存在GC ; 但是会存在OOM。

3. 线程运行诊断

3.1 案例1 cpu占用过多&解决

在这里插入图片描述

  1. 首先通过top命令定位哪个进程对cpu占用过高
  2. 根据pid 32655 我们只直到这个进程占用过高,但是我们需要知道那个线程导致的。使用ps H -eo pid,tid,%cpu | grep 32655 (用ps命令进一步定位哪个线程占用cpu过高)
    对Linux忘记的话借用deepseek回顾一下。在这里插入图片描述
    在这里插入图片描述
  3. 使用jdk提供的工具,jstack 进程id
    在这里插入图片描述
    我们已经知道是线程32655的导致的,可以直接根据线程编号,找到对应的输出信息。但是注意,32655是10进制的,但是jstack输出的信息是16进制的,所以先换算一下。
    在这里插入图片描述
    这里得到7F99,找到对应的代码。根据线程id7f99找到对应的包下的java代码,第8行。
    在这里插入图片描述
  • 发现原来是代码写了while(true) 死循环,导致CPU高。
  • 当然这里只是一个举例,实际情况要看线上的具体问题和代码。
    在这里插入图片描述

3.2 案例2 程序运行很长时间没有结果

这里是引用
一直滑倒最后看到一个死锁问题。这也是为啥不输出的原因。
在这里插入图片描述
再看具体的Java代码,其实也是很好理解。如果不理解也没关系,重温锁的知识或者死锁的产生等即可。
在这里插入图片描述

4. 拓展知识&问题辨析

4.1 栈的内存越大越好嘛?(不是)

栈越大 内存分配的栈越少,栈越少 线程越少。所以栈别太大,越小线程越多,也不能太小,太小栈溢出。【一般采用系统默认就好】

4.2 方法内的局部变量是否线程安全?(是线程安全的)

4.2.1 局部变量全在方法中

不会有线程安全问题,每个局部变量都在各自的栈帧中,线程不共享。

static void m1(){int x=0;for (int i=0;i<1000;i++){x++;}System.out.println(x);}

4.2.2 局部变量可能逃离方法

总结就是具体问题具体分析,要注意局部变量逃离本方法的问题。

//线程安全public static void m1() {StringBuilder sb = new StringBuilder();sb.append(1);sb.append(2);sb.append(3);System.out.println(sb);}//线程不安全,StringBuilder作为参数传递进来,就意味着有可能有其他线程能访问到它。就不再是线程私有的了。public static void m2(StringBuilder sb) {sb.append(1);sb.append(2);sb.append(3);System.out.println(sb);}//线程不安全,返回值也是StringBuilder,所以其他线程能访问到它。public static StringBuilder  m3() {StringBuilder sb = new StringBuilder();sb.append(1);sb.append(2);sb.append(3);return sb;}

4.3 可能抛出的异常?

StackOverFlowError?OutOfMemoryError?

  • Java 虚拟机规范允许Java栈的大小是动态的或者是固定不变的。 如果采用固定大小的Java虚拟机栈,那每一个线程的Java虚拟机栈容量可以在线程创建的时候独立选定。如果线程请求分配的栈容量超过Java虚拟机栈允许的最大容量,Java虚拟机将会抛出一个
    StackOverflowError 异常。
  • 如果Java虚拟机栈可以动态扩展,并且在尝试扩展的时候无法申请到足够的内存,或者在创建新的线程时没有足够的内存去创建对应的虚拟机栈,那Java虚拟机将会抛出—个
    OutOfMemoryError 异常。

4.4 什么情况下会发生栈内存溢出?

一、局部数组过大。当函数内部的数组过大时,有可能导致堆栈溢出。(栈帧过大)
二、递归调用层次太多。递归函数在运行时会执行压栈操作,当压栈次数太多时,也会导致堆栈溢出。(栈帧过多)

对于第1种情况可能会发生在对象转换JSON的时候,如Dept中有Emp,Emp中有Dept,无线循环,可以使用
@JsonIgnore
private Dept dept; 忽略即可。

在这里插入图片描述

4.5 如何设置栈的大小?

在这里插入图片描述

-Xss size (即:-XX:ThreadStackSize)
-Xss256k或者-XX:ThreadStackSize=256k都可以
我们看栈大小window下可能会显示0
在这里插入图片描述

  • 设置10124K
    添加VM options在这里插入图片描述在这里插入图片描述

4.6 补充栈帧的内部结构

这里是引用

重要的两个(局部变量表&操作数栈)

可以IDEA插件中下载jclasslib插件来看代码

4.6.1 局部变量表

局部变量表(local variables)
● 局部变量表也被称之为局部变量数组或本地变量表。
● 定义为一个数字数组,主要用于存储方法参数和定义在方法体内的局部变量,这些数据类型包括各类基本数据类型(8种)、对象引用(reference),以及returnAddress类型
● 局部变量表所需的容量大小是在编译期确定下来的,并保存在方法的Code属性的maximum local variables数据项中。在方法运行期间是不会改变局部变量表的大小的。
● 方法嵌套调用的次数由栈的大小决定。一般来说,栈越大,方法嵌套调用次数越多。对一个函数而言,它的参数和局部变量越多,使得局部变量表膨胀,它的栈帧就越大,以满足方法调用所需传递的信息增大的需求。进而函数调用就会占用更多的栈空间,导致其嵌套调用次数就会减少。
● 局部变量表中的变量只在当前方法调用中有效。在方法执行时,虚拟机通过使用局部变量表完成参数值到参数变量列表的传递过程。当方法调用结束后,随着方法栈帧的销毁,局部变量表也会随之销毁。
在这里插入图片描述

4.6.2 操作数栈

操作数栈(Operand Stack)
● 我们说Java虚拟机的解释引擎是基于栈的执行引擎,其中的栈指的就是操作数栈。
● 每一个独立的栈帧中除了包含局部变量表以外,还包含一个后进先出(Last-In-First-Out)的操作数栈,也可以称之为表达式栈(Expression Stack)。
● 操作数栈就是JVM执行引擎的一个工作区,当一个方法刚开始执行的时候,一个新的栈帧也会随之被创建出来,这个方法的操作数栈是空的。
● 每一个操作数栈都会拥有一个明确的栈深度用于存储数值,其所需的最大深度在编译期就定义好了,保存在方法的Code属性中,为max_stack的值。
栈中的任何一个元素都是可以任意的Java数据类型。
32bit的类型占用一个栈单位深度
64bit的类型占用两个栈单位深度
● 操作数栈,在方法执行过程中,根据字节码指令,并非采用访问索引的方式来进行数据访问的,而是只能通过标准的入栈(push)和出栈(pop)操作,往栈中写入数据或提取数据来完成一次数据访问。
某些字节码指令将值压入操作数栈,其余的字节码指令将操作数取出栈。使用它们后再把结果压入栈。比如:执行复制、交换、求和等操作
如果被调用的方法带有返回值的话,其返回值将会被压入当前栈帧的操作数栈中,并更新PC寄存器中下一条需要执行的字节码指令。

  • 操作数栈,主要用于保存计算过程的中间结果,同时作为计算过程中变量临时的存储空间。

这里做一下简单的介绍,具体对于栈的深度,以及有过slot的复用,每个类型占多少大小等后续复习继续更新吧。

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

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

相关文章

文章记单词 | 第104篇(六级)

一&#xff0c;单词释义 keyboard /ˈkiːbɔːrd/ n. 键盘underlying /ˌʌndərˈlaɪɪŋ/ adj. 潜在的&#xff1b;根本的&#xff1b;基础的June /dʒuːn/ n. 六月tactics /ˈtktɪks/ n. 战术&#xff1b;策略&#xff1b;手段south /saʊθ/ n./adj./adv. 南方&#x…

中宏立达与天空卫士达成战略合作

战略合作篇 中宏立达-天空卫士 2025年5月23日&#xff0c;中宏立达与天空卫士在中宏立达集团总部北京丽金智地中心正式签署战略合作协议。中宏立达总经理王博先生与天空卫士高级副总裁兼首席运营官巩文坚先生代表双方签署协议。这标志着两家领军企业在数字安全领域的深度合作正…

RxJS 高阶映射操作符详解:map、mergeMap 和 switchMap

1. map 操作符 map 是最基本的转换操作符&#xff0c;用于对 Observable 发出的每个值进行一对一转换。 基本特点&#xff1a; 同步操作一对一转换不改变 Observable 的发出时机 详细示例&#xff1a; import { of } from rxjs; import { map } from rxjs/operators;// 示…

基于stm32的多旋翼无人机(Multi-rotor UAV based on stm32)

由于一直在调试本项目&#xff0c;好久没有发文章&#xff0c;最近本项目的PID调试初见成效&#xff01;开始正文前首先感谢各位粉丝的支持&#xff0c;以及对本项目技术上支持的老师以及师兄&#xff0c;谢谢你们&#xff01; 对应源码及文件&#xff1a;源码及文件下载 基于…

量子传感器:开启微观世界的精准探测

随着量子技术的飞速发展&#xff0c;量子传感器逐渐成为前沿科技领域的热门研究方向。量子传感器利用量子力学的特性&#xff0c;能够实现对物理量的极高精度测量&#xff0c;其应用范围涵盖了基础科学研究、医学诊断、环境监测以及国防安全等多个领域。本文将深入探讨量子传感…

河道管网排口在线监测系统解决方案

一、方案概述 我国作为世界上河流数量最为丰富的国家之一&#xff0c;拥有众多历史悠久的壮阔江河流域。然而&#xff0c;伴随经济社会的迅猛发展&#xff0c;河湖管理与保护面临诸多新挑战&#xff0c;诸如河道干涸、湖泊萎缩、水环境恶化以及河湖功能退化等问题&#xff0c;对…

Foldseek快速蛋白质结构比对

1. 下载和安装 Foldseek 如果只是单个蛋白质结构的序列比对&#xff0c;我们只需要用Foldseek 的网站服务 https://search.foldseek.com/search 上传我们的蛋白质结构并选择想要进行比对的数据库即可&#xff0c;这里不做重点讲解。做生物信息学研究&#xff0c;我们难免需要批…

宏山激光韩国釜山开放日圆满举行,服务本地化再提速

5月21日-22日&#xff0c;宏山激光在韩国釜山展厅举办了主题为“韩国本地服务领导者”的开放日活动&#xff0c;此次活动聚焦韩国市场&#xff0c;通过沉浸式参观和深度交流&#xff0c;全面展示宏山激光本地化服务体系的建设成果&#xff0c;彰显其服务本地、深耕市场的坚定决…

大模型「瘦身」指南:从LLaMA到MobileBERT的轻量化部署实战

大模型「瘦身」指南&#xff1a;从LLaMA到MobileBERT的轻量化部署实战 系统化学习人工智能网站&#xff08;收藏&#xff09;&#xff1a;https://www.captainbed.cn/flu 文章目录 大模型「瘦身」指南&#xff1a;从LLaMA到MobileBERT的轻量化部署实战摘要引言一、轻量化技术…

JavaScript篇:函数作用域与作用域链探秘

大家好&#xff0c;我是江城开朗的豌豆&#xff0c;一名拥有6年以上前端开发经验的工程师。我精通HTML、CSS、JavaScript等基础前端技术&#xff0c;并深入掌握Vue、React、Uniapp、Flutter等主流框架&#xff0c;能够高效解决各类前端开发问题。在我的技术栈中&#xff0c;除了…

Robust Kernel Estimation with Outliers Handling for Image Deblurring论文阅读

Robust Kernel Estimation with Outliers Handling for Image Deblurring 1. 论文的研究目标与实际问题意义1.1 研究目标1.2 实际问题与产业意义2. 论文的创新方法、模型与优势2.1 核心思路2.2 关键公式与技术细节2.2.1 非线性模糊模型与能量函数2.2.2 中间潜像更新与IRLS2.2.3…

nginx配置跨域请求,后台不用配置啦,完美

允许全部把域名改* server { listen 22222; server_name localhost; location / { if ($request_method OPTIONS) { add_header Access-Control-Allow-Origin http://localhost:8080; add_header Access-Control-Allow-Headers *; add_header Access-Control-…

[特殊字符] 构建高内聚低耦合的接口架构:从数据校验到后置通知的分层实践

在现代企业系统开发中&#xff0c;接口结构设计的质量直接影响系统的稳定性、扩展性与可维护性。随着业务复杂度上升&#xff0c;单一层次的接口实现往往难以应对功能膨胀、事务一致性、后置扩展等需求。因此&#xff0c;我们提出一种面向复杂业务场景的接口分层模型&#xff0…

MySQL 5.7 实战:JSON 字段提取、Base64 解码与引号问题全解析

一、背景与问题场景 在 MySQL 数据库中&#xff0c;存储 JSON 格式数据&#xff08;如用户行为日志、配置参数、扩展信息&#xff09;的场景日益普遍。当需要从 JSON 字段中提取特定键值&#xff08;如info&#xff09;并进行 Base64 解码时&#xff0c;常遇到以下问题&#x…

1.2.1+1.2.2计算机硬件的基本组成

知识总览 早期冯诺依曼计算机&#xff1a;从人工-》自动 出现原因&#xff1a; 埃尼阿克计算机每执行一条指令都需要人工接线揽&#xff0c;虽然计算机处理的快&#xff0c;但是人工接线可能慢&#xff0c;效率低&#xff0c;于是出现冯诺依曼计算机&#xff0c;把要执行的指…

Spring AI 1.0 GA 正式发布

Spring AI 1.0 GA 正式发布 快速入门核心特性1. **增强型 LLM&#xff08;大语言模型&#xff09;**2. **MCP 协议支持**3. **RAG&#xff08;检索增强生成&#xff09;**4. **评估与监控**5. **智能代理&#xff08;Agents&#xff09;** 下一步计划 VMware Spring 团队 Mark …

亚马逊云科技推出Anthropic新一代模型

5月23日 亚马逊云科技宣布在Amazon Bedrock中推出Anthropic的最新一代模型Claude Opus 4和Claude Sonnet 4。这两款全新混合推理模型能够根据需求在快速响应和深度思考模式间灵活切换&#xff0c;为编码、高级推理和多步骤工作流领域带来全新标准。它们不仅能在复杂的长时间推理…

无人机开启未来配送新篇章

低空物流&#xff08;无人机物流&#xff09;是利用无人机等低空飞行器进行货物运输的物流方式&#xff0c;依托低空空域&#xff08;通常在120-300米&#xff09;实现快速、高效、灵活的配送服务。它是低空经济的重要组成部分&#xff0c;广泛应用于快递配送、医疗物资运输、农…

数据赋能(234)——数据管理——标准化原则

概述 标准化原则的重要性体现在确保数据的格式、结构和命名的一致性。这不仅可以提高数据的质量&#xff0c;还能促进数据的有效共享、交换和利用。以下是标准化原则的重要性的具体体现&#xff1a; 提高数据通用性&#xff1a;遵循数据标准和规范&#xff0c;确保不同系统、…

【Linux笔记】——线程池项目与线程安全单例模式

&#x1f525;个人主页&#x1f525;&#xff1a;孤寂大仙V &#x1f308;收录专栏&#x1f308;&#xff1a;Linux &#x1f339;往期回顾&#x1f339;&#xff1a; 【Linux笔记】——简单实习一个日志项目 &#x1f516;流水不争&#xff0c;争的是滔滔不息 一、线程池设计二…