内存管理机制
jvm的内存划分:java堆、虚拟机栈、本地方法栈、方法区、程序计数器
-
堆:线程共享的一块区域,存放实例化的数组或对象、GC堆
-
虚拟机栈:线程私有的数据、每个java方法执行的同时会创建一个栈帧、
栈帧中存放局部变量表、操作数栈、动态链接、方法返回地址 -
程序计数器:线程私有,字节码行号指示器。
-
方法区:和堆一样是各个线程共享的内存区域,别名Non-heap(非堆,和堆区分)
存放类信息、常量、静态变量 -
本地方法栈:存放native方法。
注意: 运行时常量池:存放编译期时生成的各种字面量和符号引用
字面量:字面量可以理解为实际值
栈->虚拟机栈
-
局部变量表:用于存放方法参数和方法内部定义的局部变量 局部变量以变量槽(slot)为最小单位,boolean, byte,char,short,int,float,reference(对象实例的引用),
returnAddress类型的数据都是32为,long、double是64位 -
操作数栈:开始方法执行时,操作数栈为空,执行过程中,各种字节码指令往操作数栈中写入和提取内容,操作数栈中的每个元素可以是任意的java类型,
包括long和double(64位物理内存空间), 32位数据类型为1,64位数据类型为2, ***注意:byte,int,char
***注意压入:byte,int,char 操作数栈之前转为int,这也就解释了为什么
byte类型相加得到int类型的结果***
-
动态链接:class文件中的常量池存有大量的符号引用,
一部分在类加载阶段或者第一次使用讲符号引用转化为直接引用->静态解析
另一部分在每一次运行期间转化为直接引用->动态链接 -
返回地址:一个方法执行时两种方式退出 第一种遇到任意一个方法返回的字节码指令
第二种遇到了异常,并且异常没有在方法体内得到处理
访问次数
访问堆的一个具体单元:
第一种需要两次访问内存(句柄访问),第一次得取得指针,第二次才是真正得数据,
第二种直接引用访问一次,
访问栈的一个具体单元:
栈只需访问一次。堆的内容被操作系统交换到外存比栈的概率比栈大,栈一般是不会被交换出去的。