java内存模型
这篇文章是根据java虚拟机中的描述作的整理笔记,有错误的地方还望各位兄弟指正。java内存模型
1. 堆(Heap)
每个java虚拟机有一个堆,所有线程共享。堆是被用来存储所有类实例、数组的运行时数据区。
堆在虚拟机启动时创建。
2. 栈
每个java虚拟机线程都有一个私有的,与线程同时创建的栈,java虚拟机栈存储虚拟机的帧(frame),在线程启动时创建,线程结束时销毁。
java栈的功能等价于传统语言例如c的栈,它存储本地变量与部分结果,并参与方法的调用与返回。
3. 帧(frame)
java虚拟机帧用于存储数据、部分结果,以及运行动态链接,返回方法的值和调度异常。
每次调用方法时都创建一个新的帧。在方法结束时撤销,无论是正常结束还是异常退出。
帧从创建该帧的线程的栈中分配。
每个帧有它自己的操作变量集和自己的操作数栈。
当调用一个方法,控制转到新方法时一个新的帧被创建并被定义为当前帧,调用该方法的帧被压入栈中,知道当前方法结束。如果方法有返回值,则当前帧把结果传递回上一个帧,然后当前帧被抛弃上一个帧成为当前帧。
一个线程创建的帧是局部的,不能被其它线程共享,这也就是为什么方法局部变量是线程安全的。
4. 本地方法栈
java虚拟机实现可以使用传统的的栈,通俗的叫“c栈”来支持native方法。这些语言不是用java语言编写的。他们通常在线程创建时分配在线程上。
5. 方法区
java虚拟机有一个所有线程共享的方法区。方法区类似传统语言中存储编译后机器码的内存存储区(又称代码段)。
它存储每个类结构,例如
常量池
字段(类的属性)
方法数据
方法、构造函数等的代码
方法区在虚拟机启动时创建,
方法去逻辑上是放在堆中,但是java虚拟机第二版的规范没有规定是否需要通过gc回收空间,及方法区的存储位置、管理策略。
6. 常量池
常量池是每个类或者接口的class文件中的常量表的运行时表示。包括编译时已知的数值文字、运行时解析的方法和字段的引用。
常量池的功能类型与传统语言的符号表,但比符号表包含更多的数据。
每个常量池在虚拟机的方法区分配。
在class文件被虚拟机成功装载时创建。
7. PC寄存器
程序计数寄存器,每个虚拟机线程都有它自己的pc寄存器。该pc寄存器与本地编程语言(例如c)的概念不同,该pc寄存器指向的是虚拟机机器码在内存中的位置,并不是本地机器码在内存中的位置。
如果正在被线程执行的代码是native,则虚拟机的pc寄存器没有定义。如果不是native则pc寄存器包含当前正在被执行的java虚拟机指令的址。
http://dl.iteye.com/upload/attachment/427248/3812d9a7-7503-36a9-9022-6359f9ace865.jpg
图中的cache是用于缓存主存中的数据,虚拟机中允许线程缓存主存的数据,但是缓存的数据是存放在什么地方暂时不知,可能是在线程中对应cpu寄存器的一块内存区域。
页:
[1]