Java内存区域:
程序计数器(Program Counter Register)
(1)线程私有
(2)当线程在执行一个Java方法时,该计数器记录的是正在执行的虚拟机字节码指令的地址;
当线程在执行的是Native方法(调用本地操作系统方法)时,该计数器的值为空。
(3)唯一一个在Java虚拟机规范中么有规定任何OOM(内存溢出:OutOfMemoryError)情况的区域。
Java虚拟机栈(Java Virtual Machine Stacks)
(1)线程私有的,生命周期与线程相同。
(2)虚拟机栈描述的是Java方法执行的内存模型:每个方法被执行的时候都会同时创建一个栈帧,栈帧用于存储局部变量表、操作数栈、动态链接、方法返回地址和一些额外的附加信息。在编译程序代码时,栈帧中需要多大的局部变量表、多深的操作数栈都已经完全确定了,并且写入了方法表的Code属性之中。因此,一个栈帧需要分配多少内存,不会受到程序运行期变量数据的影响,而仅仅取决于具体的虚拟机实现。
(3)在Java虚拟机规范中,对这个区域规定了两种异常情况:
a) 如果线程请求的栈深度大于虚拟机所允许的深度,将抛出StackOverflowError异常。
b) 如果虚拟机在动态扩展栈时无法申请到足够的内存空间,则抛出OutOfMemoryError异常。
本地方法栈(Native Method Stacks)
(1)线程私有
(2) 该区域与虚拟机栈所发挥的作用非常相似,只是虚拟机栈为虚拟机执行Java方法服务,而本地方法栈则为使用到的本地操作系统(Native)方法服务。与虚拟机栈一样,本地方法栈也会抛出StackOverflowError异常和OutOfMemoryError异常。
Java堆(Java Heap)
(1)线程共享,没有空间时将抛出OutOfMemoryError异常。
(2)所有的对象实例以及数组都要在堆上分配(例外:逃逸分析技术比如栈上分配)
(3)细分:
Young Generation(年轻代)、Old Generation(年老代)以及Perm Generation(永久代)。其中的Young Generation(年轻代),又分为Eden、From和To,其中From和To又统称为Survivor Spaces(幸存区)。
方法区(Method Area)
(1)线程共享
(2)它用于存储已经被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。方法区域又被称为“永久代”,但这仅仅对于Sun HotSpot来讲,JRockit和IBM J9虚拟机中并不存在永久代的概念。垃圾回收行为在这个区域是比较少见的。
(3)根据Java虚拟机规范的规定,当方法区无法满足内存分配需求时,将抛出OutOfMemoryError异常。
运行时常量池 (Ruentime Constnat Pool)
(1)属于方法区的一部分。
(2)用于Class文件的各种字面量和符号引用。
(3)运行时常量池相对于Class文件常量池的另一个重要特征是具备动态性,Java语言并不要求常量一定只能在编译期产生,运行期间也可能将新的常量放入池中,如String类的intern()方法。
直接内存(Direct Memory)
直接内存并不是Java虚拟机中的内存区域,它直接从操作系统中分配,可以利用DirectByteBuffer实现Netty的零拷贝。
jdk1.8变化
JDK 1.6下,会出现“PermGen Space”的内存溢出,而在 JDK 1.7和 JDK 1.8 中,会出现堆内存溢出,并且 JDK 1.8中 PermSize 和 MaxPermGen 已经无效。因此,可以大致验证 JDK 1.7 和 1.8 将字符串常量由永久代转移到堆中,并且 JDK 1.8 中已经不存在永久代的结论。
元空间的本质和永久代类似,都是对JVM规范中方法区的实现。不过元空间与永久代之间最大的区别在于:元空间并不在虚拟机中,而是使用本地内存。因此,默认情况下,元空间的大小仅受本地内存限制,但可以通过以下参数来指定元空间的大小:
-XX:MetaspaceSize,初始空间大小,达到该值就会触发垃圾收集进行类型卸载,同时GC会对该值进行调整:如果释放了大量的空间,就适当降低该值;如果释放了很少的空间,那么在不超过MaxMetaspaceSize时,适当提高该值。
-XX:MaxMetaspaceSize,最大空间,默认是没有限制的。
除了上面两个指定大小的选项以外,还有两个与 GC 相关的属性:
-XX:MinMetaspaceFreeRatio,在GC之后,最小的Metaspace剩余空间容量的百分比,减少为分配空间所导致的垃圾收集
-XX:MaxMetaspaceFreeRatio,在GC之后,最大的Metaspace剩余空间容量的百分比,减少为释放空间所导致的垃圾收集