JVM原理之运行时数据区

JVM虚拟机
1. JVM在运行时主要包含java堆,方法区,程序计数器,JVM栈,本地方法栈。其中JAVA堆和方法区归所有线程共有,而JVM栈和程序计数器归线程私有。
程序计数器
  1. 程序计数器主要是执行线程中的指令,在多核环境中,线程需要进行切换。线程获得CPU的执行后要恢复到原来的执行位置,这就是需要程序计数器保存当前线程执行位置。每个线程都有自己独立的计数器。
  2. 如果线程正在执行一个JAVA方法,则程序计数器记录的是当前字节码指令。
虚拟机栈
  1. JAVA虚拟机栈是线程私有的,生命周期与线程相同。虚拟机栈描述的是java方法的内存模型。每个方法在执行时,线程都会创建一个栈帧,用于存储局部变量表,操作数栈,动态链接,方法出口等信息。
    1.1 局部变量表存储了基本类型和引用类型和returnAddress类型。局部变量表的空间在编译期间已经确定,在方法运行期间不会改变。
  2. 每一个JAVA方法的执行实际上就是栈帧在的入栈和出栈操作。
本地方法栈
  1. 本地方法栈是JVM虚拟机用来调用本地方法,不同的虚拟机实现本地方法栈不同。
JAVA堆
  1. JAVA堆是JVM内存管理中最大的一块内存区域,是所有线程共享的区域。堆在JVM启动时创建,主要存放对象实例和数组。JAVA堆可以处于物理上不连续的空间,只要逻辑上连续即可。
  2. 现在的垃圾收集主要采用分代收集,通常将JAVA堆分为新生代和老年代。其中,新生代又分为Eden区,from surivior区,to surivior区。通常Eden区和surivior区比例为8:2。
  3. 堆的大小都是可以控制的,通过-Xms和-Xmx进行控制。
方法区
  1. 方法区同java堆一样,都是所有线程共享的区域,主要存储被加载类的信息,常亮,静态变量,及时编译器变异后的代码。
  2. 对于HotSpot而言,GC分代收集时,会回收方法区,也称方法区为”永久代”。这样垃圾收集器就可以像管理java堆一样管理方法区的内存。
  3. 垃圾收集行为在方法区是很少出现的,即使出现了,回收内存成果也是不怎么好。在方法区进行垃圾回收主要是回收常亮池和类型的卸载。
运行时常量池
  1. 运行时常量池是方法区的一部分。Class文件中除了有类的版本,字段,方法,接口等信息,还有一项信息就是常量池。
  2. 常量池另外一个重要特征就是动态性,运行期间也可以将新的常量放入池中。常量池中主要存放符号引用和各种字面量。
直接内存
  1. JDK中NIO,采用了通道和缓冲一种新的I/O方式,NIO可以采用Native函数直接分配堆内存以外的内存。即不占用JVM内存。
  2. 在JVM中同时存储了一个DirectByteBuffer对象,它可以直接操纵直接内存。DirectByteBuffer对象的引用指向直接内存。
  3. 直接内存的存在避免了JVM和本地堆中来回复制数据。

对象创建

  1. 在应用程序中当生成一条New指令时,JVM就会从常量池中寻找代表该类型的符号引用,如果能找到该类的类型符号,则说明已经加载该类。如果没有找到,则需要重新加载该符号代表的类。
  2. 找到代表该类的符号引用,JVM会分配一块与该对象大小相等内存空间。分配内存空间时,可以采用指针碰撞法或空闲列表方式。
    这里写图片描述
对象访问定位
  1. 在JVM堆中生成对象之后,访问对象的方式主要通过reference来访问。在JVM中reference类型在JVM规范中只规定了一个指向对象的引用,但是没有规定通过何种方式去定位,查找到对象。
  2. 目前主流的reference访问对象方式主要有通过句柄和直接指针两种方式。在流行的HotSpot中,采用直接指针方式进行定位对象。
    2.1 直接指针访问是指 reference中存放了对象实例的指针(即对象地址)和对象类型数据指针的地址,通过reference可以直接在堆中定位到对象实例。对象类型的指针也是存放在堆中,但是该类型数据存放在方法区中。说起来有点拗口,通过图可以直观表示一下:
    这里写图片描述
    2.2 句柄方式访问是指在JVM堆中单独分配一块内存,用来存放句柄池。句柄池中存放的是都是句柄,而句柄中包含了对象实例数据与对象类型数据的地址信息。reference中存放的是句柄的地址。
    这里写图片描述
    2.2.1 上图可以看出,使用句柄访问对象时,reference中存放的是句柄的地址,句柄是存放在JVM堆中的句柄池中,句柄中存放了对象数据实例指针和对象类型数据指针。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值