qidao123.com技术社区-IT企服评测·应用市场

标题: Java假造机 - 步伐计数器和假造机栈 [打印本页]

作者: 鼠扑    时间: 前天 17:10
标题: Java假造机 - 步伐计数器和假造机栈
Java运行时数据区

首先介绍Java运行时数据之前,我们要相识,对于计算机来说,内存是非常重要的资源,因为内存是连接CPU与硬盘的桥梁,承载着操作体系与应用步伐的运行的基础。JVM在运行期间把它管理的内存分为若干个地区,有些地区是线程私有的,有些地区是共享的。
Java运行时数据区作为JVM在步伐实行过程中管理内存的焦点结构,重要包括方法区(存储类元数据、运行时常量池、静态变量)、堆(存放对象实例和数组,被全部线程共享且是垃圾回收的主地区)、假造机栈(每个线程私有,用于存储方法调用的栈帧,包含局部变量表、操作数栈及方法出口)、本地方法栈(支持Native方法调用)和步伐计数器(记录当火线程实行的字节码位置,确保多线程切换后能恢复实行)。其中,堆和方法区是线程共享的,而假造机栈、本地方法栈和步伐计数器为线程私有,共同协作实现Java步伐的内存分配、方法实行及多线程调理。

步伐计数器

步伐计数器(Program Counter Register)在JVM中可以当成当火线程所实行的字节码的行号指示器,在JVM的概念模子里面,字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要实行的字节码指令,它是步伐控制流的指示器。分支 、循环 、跳转 、异常处理 、线程恢复等都是依赖这个计数器来实现的。

假如步伐实行的是Java方法,计数器代表的是只在实行的假造机字节码的地址;假如实行的是本地方法,这个计数器的值为空(undefined)。此外,这个计数器地区是Java假造机规范的没有规定任何内存溢出的地方,步伐计数区既没有内存溢出,也没有垃圾回收。因为步伐计数器是很小的一块内存地区,几乎可以忽略不记,同时也是运行最快的地区。
为什么需要步伐计数器

因为CPU需要不停的切换各个线程,做完切换之后,需要知道接下来从哪里开始实行。通过使用步伐计数器生存了接下来要实行的地址,这样CPU切换过来之后就可以直接接着实行。
实行流程

  1. // 示例代码
  2. public class Demo {
  3.     public int test() {
  4.         int a = 10;
  5.         int b = 20;
  6.         int c = a + b;
  7.         String d = "abd";
  8.         System.out.println(d);
  9.         return d.length();
  10.     }
  11. }
复制代码
通过javap -c Demo.class反编译后:
  1. 0 bipush 10
  2. 2 istore_1
  3. 3 bipush 20
  4. 5 istore_2
  5. 6 iload_1
  6. 7 iload_2
  7. 8 iadd
  8. 9 istore_3
  9. 10 ldc #2 <abd>
  10. 12 astore 4
  11. 14 getstatic #9 <java/lang/System.out : Ljava/io/PrintStream;>
  12. 17 aload 4
  13. 19 invokevirtual #15 <java/io/PrintStream.println : (Ljava/lang/String;)V>
  14. 22 aload 4
  15. 24 invokevirtual #21 <java/lang/String.length : ()I>
  16. 27 ireturn
复制代码

假造机栈

假造机栈(Java Virtual Machine Stack)是JVM内存模子中与线程实行密切相关的焦点地区,用于存储方法调用的栈帧(Stack Frame)。它是线程私有的内存空间,每个线程在创建时都会分配一个独立的假造机栈,其生命周期与线程同等。以下从设计目标、焦点结构、运行机制到常见问题全面解析。
假造机栈作用

假造机栈的焦点功能是支持Java方法的调用与实行,具体包括:

假造机栈焦点结构

假造机栈由多个栈帧(Stack Frame)构成,每个栈帧对应一个方法的调用。栈帧包含以下焦点部分:
  1. public void demo(int a, String b) {
  2.     double c = 3.14;
  3.     Object d = new Object();
  4. }
复制代码
  1. 局部变量表结构:
复制代码

  1. int result = 1 + 2;
复制代码
  1. iconst_1  // 压入1
  2. iconst_2  // 压入2
  3. iadd      // 弹出1和2,相加后压入3
  4. istore_1  // 将3存储到局部变量表索引1
复制代码


运行机制

方法返回时:栈帧弹出,开释内存。
示例:
  1. public class StackOverflowDemo {
  2.     public static void main(String[] args) {
  3.         infiniteCall(); // 无限递归调用
  4.     }
  5.     static void infiniteCall() {
  6.         infiniteCall();
  7.     }
  8. }
复制代码
报错信息:
  1. Exception in thread "main" java.lang.StackOverflowError
复制代码
默认值:不同JVM实现不同(HotSpot Linux x64默认1MB)。

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。




欢迎光临 qidao123.com技术社区-IT企服评测·应用市场 (https://dis.qidao123.com/) Powered by Discuz! X3.4