一.运行时数据区域
1.程序计数器
线程私有的一块区域,用来指引虚拟机下条应该执行的指令。
这块区域是虚拟机规范中唯一一块没有规定任何OutOfMemoryError区域。
2.java虚拟机栈
也就是我们常说的栈,线程私有的。
虚拟机栈描述的是java方法执行的内存模型。
虚拟机栈的局部变量表储存着编译期间所知道的所有数据类型(int,reference 类型).
虚拟机栈存在两种异常,stackOverFlowError和OutOfMemoryError
本地方法栈痛java虚拟机栈作用一样,但是他是用来执行本地方法的。
3.java堆
java堆(java heap)是java虚拟机所管理的内存中最大的一块。gc回收的主要区域。所有线程共享的区域。
几乎所有的对象实例都是存放在该区域。
由于现代的收集器采用的都是分代回收,因此该区域也可以分为新生代(Eden,from survivor,to survivor,比例8:1:1),老年代。
4.方法区
方法区也是线程共享的,用来存储已被加载的类的信息,常量,静态变量,即时编译器编译的代码等。
java虚拟机规范把该区域归为java堆得逻辑区域,java虚拟机对这个区域的限制很宽松,Hotspot虚拟机也把这个区域叫做永久代。
垃圾收集行为在这个区域很少出现。
二.java对象创建
1.对象创建过程
java虚拟机遇到new执行——>检查常量池中是否加载了该类——>没有的话直接编译报错,加载了的话分配内存(分配内存方法:指针碰撞,空闲列表)
——>初始化对象——>java程序使用
2.对象内存布局
java对象包含对象头,实例数据,对齐填充三部分
3.对象的访问定位
两种方法:句柄和直接指针
句柄访问的方法时,引用是句柄的地址,堆中分出一个句柄池,句柄包含两部分信息,对象实例数据(java堆)和类型数据(方法区)
直接指针方法时,引用是对象的内存地址。