6.Java虚拟机(jvm)

Java运行时虚拟机内存区域划分(jdk18)
在这里插入图片描述

  1. 元空间(Metaspace)
    元空间(Metaspace)从java8开始替换掉了原来的方法区(Method Area)。相比方法区(Method Area)在元空间中各个项目会共享同样的class内存空间,能提高内存的利用率且更利于垃圾回收;另外元空间并不在虚拟机中,而是使用本地内存,因此元空间的大小仅受本地内存限制,但可以通过以下参数来指定元空间的大小
    -XX:MetaspaceSize,初始空间大小,达到该值就会触发垃圾收集进行类型卸载,同时GC会对该值进行调整:如果释放了大量的空间,就适当降低该值;如果释放了很少的空间,那么在不超过MaxMetaspaceSize时,适当提高该值。
    -XX:MaxMetaspaceSize,最大空间,默认是没有限制的。
    -XX:MinMetaspaceFreeRatio,在GC之后,最小的Metaspace剩余空间容量的百分比,减少为分配空间所导致的垃圾收集。
    -XX:MaxMetaspaceFreeRatio,在GC之后,最大的Metaspace剩余空间容量的百分比,减少为释放空间所导致的垃圾收集

方法区(Method Area)又称作非堆(Non-Heap)、永久代(PermGen),是各个线程共享的内存区域,它用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据,java8中已经没有方法区了,取而代之的是元空间(Metaspace)。
方法区满时,无法在分配空间,就会抛出内存溢出的异常(OutOfMemoneyError)。
方法区在JDK8中被完全的移除了。所以方法区的参数-XX:PermSize和-XX:MaxPermSize也被移除了。

  1. 堆(Heap)
    在这里插入图片描述
    堆(Heap)是Java 虚拟机所管理的内存中最大的一块,被所有线程共享的区域在虚拟机启动时创建。堆里面存放的都是对象的实例(new 出来的对象都存在堆中)。
    堆是垃圾收集器管理的主要区域,因此很多时候也被称做“GC 堆”。堆又可分为新生代和老年代(Tenured Gen),更细一点划分新生代有可分为Eden Space(伊甸园区),Survivor Space(幸存者区)。
    Eden:新创建的对象就会在Eden Space(伊甸园区)。当GC机制执行后没有被引用的对象将会被kill掉,其他的会进入Survivor Space(幸存者区)。
    Survivor:保存新生代GC后还存活的对象。
    Tenured Gen:对象存活时间比较长,经过多次新生代的GC(默认是15次)如果还存活将进入Tenured Gen(老年代)。

当堆中分配的对象实例过多,且大部分对象都在使用,就会报内存溢出异常(OutOfMemoneyError)。

  1. 虚拟机栈(vm stacks)
    虚拟机栈是线程私有的,生命周期与线程相同。创建线程的时候就会创建一个java虚拟机栈。
    每个方法被执行的时候都会同时创建一个栈帧(Stack Frame ①)用于存储局部变量表、操作栈、动态链接、方法出口等信息。每一个方法被调用直至执行完成的过程,就对应着一个栈帧在虚拟机栈中从入栈到出栈的过程。
    栈帧又分为一下几个区域:局部变量表、操作数栈、动态连接、方法出口等。
    如果线程请求的栈深度大于虚拟机所允许的深度,将抛出StackOverflowError 异常当扩展时无法申请到足够的内存时会抛出OutOfMemoryError 异常。

java8中基本类型的局部变量的值存放在虚拟机栈的局部变量表中,如果是引用型的变量,则只存储对象的引用地址。

  1. 本地方法栈(Native Method Stack)
    本地方法栈(Native Method Stack)与虚拟机栈所发挥的作用是非常相似的,其区别是虚拟机栈为虚拟机执行Java 方法(也就是字节码)服务,而本地方法栈则是为虚拟机使用到的Native 方法服务。虚拟机规范中对本地方法栈中的方法使用的语言、使用方式与数据结构并没有强制规定,因此具体的虚拟机可以自由实现它。本地方法栈区域也会抛出StackOverflowError 和OutOfMemoryError异常。
  2. 程序计数器(Programe Counter Register)
    程序计数器(Programe Counter Register)是一块较小的内存空间,它的作用可以看做是当前线程所执行的字节码的行号指示器,其记录当前线程执行程序的位置,通过改变计数器的值来确定执行的下一条指令,比如循环、分支、方法跳转、异常处理,线程恢复都是依赖程序计数器来完成。
    Java虚拟机多线程是通过线程轮流切换并分配处理器执行时间的方式实现的。为了线程切换能恢复到正确的位置,每条线程都需要一个独立的程序计数器,所以它是线程私有的
    如果线程正在执行的是一个Java 方法,这个计数器记录的是正在执行的虚拟机字节码指令的地址;如果正在执行的是Natvie 方法,这个计数器值则为空(Undefined)。此内存区域是唯一一个在Java 虚拟机规范中没有规定任何OutOfMemoryError 情况的区域。
  3. Java虚拟机参数说明
    -Xms size
    设置堆的初始大小(以字节为单位)。该值必须是1024的倍数且大于1 MB。附加字母k或K表示千字节,m或M指示兆字节,g或G指示千兆字节。
    -Xmx size
    设置堆内存的最大大小(以字节为单位),附加字母k或K表示千字节,m或M指示兆字节,g或G指示千兆字节。一般的服务端部署,-Xms和-Xmx设置为同样大小以避免每次GC后调整堆的大小。-Xmx 与-XX:MaxNewSize等效。默认值为物理内存的1/4。
    -Xmn size
    设置堆新生代大小(以字节为单位),附加字母k或K表示千字节,m或M指示兆字节,g或G指示千兆字节。-Xmn与-XX:NewSize等效。
    堆的年轻代区域用于新对象。GC在该区域比在其他区域更频繁地进行。如果年轻一代的规模太小,那么将会进行大量的小型垃圾收集。如果大小太大,则只执行完整的垃圾收集,这可能需要很长时间才能完成。Oracle建议您将年轻代的大小保持在整个堆大小的一半到四分之一之间
    -Xss size
    设置线程堆栈大小(以字节为单位)通常只有几百K。附加字母k或K表示KB,m或M表示MB,g或G表示GB。默认值取决于平台(如:Linux / x64(64位):1024 KB)。
    -XX:PermSize size -XX:MaxPermSize size
    设置永久区的初始空间和最大空间。也就是说,jvm启动时,永久区一开始就占用了PermSize大小的空间,如果空间还不够,可以继续扩展,但是不能超过MaxPermSize,否则会OOM。
    -XX:PermSize size -XX:MaxPermSize size在Jdk1.8中已经被弃用,被-XX:MetaspaceSize size -XX:MaxMetaspaceSize size选项取代。
    -XX:NewRatio
    新生代和年老代的堆内存占用比例。

默认的,新生代 ( Young ) 与老年代 ( Old ) 的比例的值为 1:2 ( 该值可以通过参数 –XX:NewRatio 来指定 ),即:新生代 ( Young ) = 1/3 的堆空间大小。
老年代 ( Old ) = 2/3 的堆空间大小。其中,新生代 ( Young ) 被细分为 Eden 和 两个 Survivor 区域,这两个 Survivor 区域分别被命名为 from 和 to,以示区分。
默认的,Edem : from : to = 8 : 1 : 1 ( 可以通过参数 –XX:SurvivorRatio 来设定 ),即: Eden = 8/10 的新生代空间大小,from = to = 1/10 的新生代空间大小。
‍JVM 每次只会使用 Eden 和其中的一块 Survivor 区域来为对象服务,所以无论什么时候,总是有一块 Survivor 区域是空闲着的。
因此,新生代实际可用的内存空间为 9/10 ( 即90% )的新生代空间。

-XX CompressedClassSpaceSize size
类指针压缩空间大小, 默认为1G,只有当-XX:+UseCompressedClassPointers开启了才有效。
7. JVM设置示例

JAVA_OPTS=-server -Xms***m -Xmx****m -Xmn***m -XX:MetaspaceSize=****m -XX:MaxMetaspaceSize=***m -XX:CompressedClassSpaceSize=**m

8.查看vm的所有设置参数

#jps查看java进程的pid
jps
#jinfo -flags pid或jcmd pid VM.flags查看vm的所有设置参数
jinfo -flags 14768
jcmd 14768 VM.flags
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值