从概述中了解到本章讲从概念上介绍Java虚拟机内存的各个区域,讲解这些区域的作用,服务的对象,以及其中可能产生的异常。所以本章的阅读我也将带着这些问题阅读。
1、运行时数据区域
Java虚拟机在执行java程序的过程中会把他所管理的内存划分为若干个不同的数据区域。
1.1 程序计数器
区域的作用:当前程序所执行的字节码的行号(偏移地址)指示器。
服务对象:字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要执行的字节码指令。分支,循环,跳转,异常处理,线程恢复等都需要依赖这个计数器来完成。
由于Java多线程是通过线程轮流切换并分配处理器执行时间的方式来实现的。因此为了线程切换后能恢复到切换前的状态,每条线程都需要一个独立的程序技术器。
当线程执行的是本地方法的时候,程序计数器中保存的值是空(undefined);
jvm虚拟机规范,也就没有规定,也是唯一一个没有规定 OutOfMemoryError 异常 的区域;
1.2 java虚拟机栈
区域的作用:java 方法执行的内存模型。每个方法在执行的时候都会创建一个栈帧,用于存储局部变量表,操作数栈,动态链接,方法出口等信息。
局部变量表存放编译期可知的各种基本数据类型(boolean,byte,char,int,float,long,double)、对象引用,returnAddress类型。所以其内存空间在编译期就完成分配,并完全确定,在整个方法运行期间不会改变局部变量表的大小。
线程请求的栈深度大于虚拟机所允许的深度,将抛出StackOverflowError。如果扩展时无法申请到足够的内存,就会抛出OutOfMemoryError。
1.3 本地方法栈
本地方法栈和java虚拟机栈所发挥的作用非常相似,他们之间的区别是虚拟机栈为执行java方法服务,本地方法栈则为native方法服务。
1.4 java 堆
区域的作用:是所有线程共享的一块内存区域,在JVM启动的时候创建,此内存区域的唯一目的就是存放对象实例。
Java堆是垃圾收集器管理的主要区域,因此很多时候也被称为‘GC’堆。
如果堆中没有完成内存实例分配,并且堆也无法在扩展时,将会抛出OutOfMemoryError
1.5 方法区
区域的作用:是各个线程共享的内存区域,用于存储已经被JVM加载的类信息,常量,静态变量,即时编辑器编译后的代码等数据。
如果方法区无法满足内存分配时,将会抛出OutOfMemoryError
1.6 运行时常量池
运行时常量池是方法区的一部分。Class文件中除了类的版本,字段,方法,接口等描述信息外,还有一项信息是常量池,用于存放编译期生成的各种字面量和符号引用。这部分内容将在类加载后进去方法区的运行时常量池中存放。