一、JAVA内存结构
java内存结构方法区:用于存放被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据
虚拟机栈:一个线程一个栈,一个方法一个栈帧用于存储局部变量表、操作数栈、动态链接、方法出口等信息。
注:局部变量表存放了编译期可知的各种基本数据类型(boolean、byte、char、short、int、float、long、double)、对应引用(reference类型,它不等同于对象本身,可能是一个指向对象起始地址的引用指针,也可能是指向一个代表对象的句柄或其他与此对象相关的位置)和returnAddress类型(指向了一条字节码指令的地址)。
虚拟机堆:堆是Java虚拟机所管理的内存中最大的一块。Java堆是被所有线程共享的一块内存区域,在虚拟机启动时创建,此内存区域的唯一目的就是存放对象实例,几乎所有的对象实例都在这里分配内存
程序计数器:简单讲就是一块比较小的内存空间,字节码解释器工作时就是通过改变这个计数器的值来选取吓一跳需要执行的字节码指令,分支、循环、跳转、异常处理、线程恢复等基础功能都需要依赖这个计数器来完成。
本地方法栈:与虚拟机栈所发挥的作用是非常相似的,它们之间的区别不过是虚拟机栈为虚拟机执行Java方法(也就是字节码)服务,而本地方法栈则为虚拟机使用到的Native方法服务。
二、堆内存分配
堆内存new:新生代 old:老年代
new一个对象出来后,如果创建的对象非常的大(或达到了配置的要求)会直接放入到tenured区域,否则正常来讲一般都会去eden区域待着。
survivor:在我们新生代中可以看到有2个survivor区域,这是做什么用的呢,为什么要有两个呢,原因很简单,它的存在是为了我们在新生代使用的复制算法而专门开辟的一个内存空间,survivor有两个,也有人管他们叫s0、s1或者from、to,下面讲解新生代用的复制算法,大家就知道了。
新生代GC算法:
- 当我们正常new出一个对象(A)后,对象A会留在我们的eden区域,这时我们来一波GC的洗礼,对象没有被回收(eden区清空A), 此时我们对象A会被回收到新生代里其中的某个survivor区域中(暂时用s0表示)。
- 第二波GC,对象还是没有被回收掉,这时s0中的对象A会被复制到s1中,s0清空内存,endn区中的未被回收掉的对象也会被放到s1中。
- 第三波GC,s0中的内存目前是空的,将s1中的没有被回收掉的对象再复制一份到s0中 ,s1清空内存,endn区域中未被回收的对象也会被放到s0中。
- 循环往复无穷尽也.......
注意:如果2个survivor中某个survivor如果这次是from那下一次肯定是to。讲解一下为什么是2个survivor当然是因为效率问题啦。
老年代:上面讲到,新生代会经历GC的洗礼,当某个对象执行到一定次数的GC之后还没有被回收掉,就会被扔到我们的tenured区域中了。
老年代使用的算法:Mark-Compact(标记压缩),主要是向一端进行压缩替换,将未使用的空间替换成连续的内存空间,文章后面有讲到标记压缩算法。
三、垃圾收集算法
-
Mark-Sweep(标记清除)
标记清除
问题:内存碎片化,连续的内存块比较小,一旦有比较大的对象可能就要执行fullGC,如果执行fullGC则效率较低。
-
Copying(复制算法)
复制
好处:效率较高,并且顺着做了压缩了。
问题:内存浪费,永远只能使用一半的内存。
3.Mark-Compact(标记压缩)
标记压缩
问题:向一端压缩,效率也还行,比复制的要低,标记压缩算法适用于垃圾少的区域使用,常用于老年代。
四、JVM参数
- -: 标准参数,所有jvm都应该支持
- -X: 非标准参数,每个jvm实现都不同
- -XX: 不稳定参数,下个版本可能会取消
五、JVM中的垃圾收集器
- Serial Collector
XX:_UseSerialGC
只能在单线程中使用,并且不能大于100兆 - Parallel Collector
-XX:+UseParallelGC
并发量大,不过每次垃圾收集,JVM需要停顿,停顿完才能继续执行 - CMS Collector
-XX:+UseConcMarkSweepGC
停顿时间短 - G1
-XX:+UseG1GC
不仅停顿短,同时并发大
六、常用参数设置
堆设置:
- -Xms: 初始堆大小
- -Xmx: 最大堆大小
- -Xss: 线程栈大小
- -XX:NewSize=n 设置年轻待带下
- -XX:NewRatio=n 设置年轻代和年老代的比值,如3,表示年轻代:年老代比值为1:3,年轻代占整个堆内存的1/4
- -XX:SurvivorRatio=n 设置年轻代中Eden区与两个Survivor区的比值。注意Survivor区有2个。如3,表示Eden:Survivor=3:2,一个Survivor区占整个年轻代的1/5。
- -XX:MaxPermSize=n 设置持久代大小
垃圾回收统计信息:
- -XX:+PrintGC
- -XX:+PrintGCDetails
- -Xloggc:filename 把相关日志信息记录到文件
网友评论