关于java:一文看懂JVM内存区域分布与作用

41次阅读

共计 1563 个字符,预计需要花费 4 分钟才能阅读完成。

那么咱们在开始介绍 Java 内存区域之前,咱们先放一张内存区域的图,不便咱们前面介绍的时候能够对照着看。

须知 ,本文是依据 JDK8 来介绍的。

程序计数器

首先它是线程公有的,它也称为代码的行号指示器,字节码解释器就是通过改变程序计数器的地位来确定下一行要执行的代码,它不存在 OOM。

如果线程正在执行一个 Java 办法,那么它记录的是正在执行虚拟机字节码指令的地址,如果是一个本地办法那么它的值为空。

Java 虚拟机栈

它也是线程公有的,它的申明周期和线程统一。每个线程创立时都会创立一个虚拟机栈,外部保留了一个个的栈帧,每个栈帧就对应着一次办法的调用。既然晓得了虚拟机栈外面寄存的是一个个的栈帧,那么也不难猜出虚拟机栈外面都存储了什么货色。

Java 虚拟机栈是存在 OOM 的,当线程所申请的栈的深度大于虚拟机栈的深度或者虚拟机栈能够动静扩容,当栈扩大时无奈申请到足够的内存时,就会抛出 OOM。

  • 虚拟机栈内部结构

  • 局部变量表

    次要存储办法的参数,所有的根本类型数据和对象地址,以及返回地址类型(return address)。它以变量槽为最小的存储单位,Java 虚拟机并没有规定一个变量槽占用多少内存空间,然而规定了一个变量槽能够寄存一个 32 位以内的数据类型。如果存储的数据类型超过 32 位,比方 long、double,那么就应用两个变量槽进行存储。

  • 操作数栈

    操作数栈是一个先进后出的操作数栈,当一个办法刚开始执行的时候,一个新的栈帧也会随之被创立进去,这个办法的操作数栈是空的,它次要用于保留计算过程的两头后果,同时作为计算过程中变量长期的存储空间。如果被调用的办法有返回值,那么返回值将会被压入以后栈帧的操作数栈中。操作数栈并非采纳索引的形式进行数据拜访,而是通过入栈(push)和出栈(pop)操作来实现数据的拜访。

  • 动静链接

    大白话就是,栈帧中保留了一个办法的援用,当执行办法的时候,能够拿着这个援用到运行时常量池中找到这个办法。

    动静链接的作用就是将这些办法的符号援用转换为调用办法的间接援用。

  • 办法返回地址

    就是在办法执行完结之后,要返回下一条要执行代码地位的值,也就是程序计数器的值。

    那么除了办法失常执行完结退出外,还有另外一种状况就是异样导致的办法退出,那么这种状况下是不会返回任何值的。对于抛出的异样,栈帧中不会做任何记录,然而会记录在一个异样表中。

本地办法栈

Java 虚拟机栈为虚拟机执行 Java 办法服务,本地办法栈则为虚拟机应用到的本地办法服务。像 JVM 就有好多 C 语言写的办法,这个就须要本地办法栈来执行。

Java 堆

Java 堆是虚拟机中最大的一块内存空间,它被所有的线程共享,在虚拟机启动时创立。它惟一的目标就是寄存对象实例。

如果面试被问到,所有的对象实例都是在堆中分配内存吗?这个时候你肯定要答复,不是。

随着即时编译技术的倒退提高,尤其是逃逸剖析技术的日渐弱小,栈上调配、变量替换等优化伎俩,让实例在”只在堆“中调配不再成为相对。

Java 堆是垃圾收集的次要区域,Java 堆中也经常出现新生代、老年代、永恒代等等,这里须要留神,这些并不是 Java 堆物理上的内存布局,它是作为垃圾收集器而划分一种内存布局。

办法区

办法区也是线程共享的区域,它次要用于存储被虚拟机加载的类型信息、常量、动态变量、即时编译器编译后的代码缓存等数据。

办法区它是能够被垃圾收集器进行回收的,次要针对类型的卸载和常量池的回收。

办法区也能够产生 OOM,当办法区无奈满足新的内存调配需要时,将抛出 OutOfMemoryError 异样。

运行时常量池

运行时常量池是办法区的一部分。Class 文件中除了有类的版本、字段、办法、接口等信息外,还有一项信息是常量池表,它用来存储编译期生成的各种字面量和符号援用。

如果动静链接那块没看懂,那么看了运行常量池再翻回去看看是不是好了解了。

正文完
 0