一. Sun Classic --> Exact VM -->hotspot vm (程序计数器)
二.jvm内存区域:运行时数据区线程隔离的数据区包括:程序计数器、java虚拟机栈、本地方法栈。
所有线程共享的数据区包括:java堆、方法区
程序计数器当前线程所执行的字节码的行号指示器,字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要执行的字节码指令。分支、循环、跳转、异常处理、线程恢复等基础功能都需要依赖这个计数器来完成。
栈里存放了编译期可知的各种基本数据类型(boolean、byte、char、short、int、float、long、double)、对象引用和指向了一条字节码指令的地址。
Java堆(Java Heap)是Java虚拟机所管理的内存中最大的一块,此内存区域就是存放对象实例,几乎所有的对象实例都在这里分配内存.
方法区又叫静态区:用于存储已被虚拟机加载的类信息、常量池、静态变量、即时编译器编译后的代码等数据.
三、垃圾收集器
对象的引用:强引用(垃圾收集器不会回收掉被强引用的对象。)、软引用(系统在发生内存溢出异常之前,会把只被软引用的对象进行回收。)、弱引用(垃圾回收不论内存是否不足都会回收只被弱引用关联的对象。)、虚引用。
判断对象的存活方式:引用计数算法、可达性分析(通过一系列的称为“GC Roots”的对象作为起始点,从这些节点开始向下搜索,搜索所走过的路径称为引用链,当一个对象到GC Roots没有任何引用链相连(即不可达)时,则证明此对象是不可用的)。
对象的生死:不可达的对象真正死亡需要两次标记:如果调用finalize()方法计局可以被救活,不被回收。
标记-清除算法:最基础的收集算法是“标记-清除”(Mark-Sweep)算法,此方法分为两个阶段:标记、清除:效率低下,空间碎片化严重(需要整理)。
复制算法:它将可用内存按容量划分为大小相等的两块,每次只使用其中的一块。当这一块的内存用完了,就将还存活着的对象复制到另外一块上面,然后再把已使用过的内存空间一次清理掉。(浪费空间)
GC方式:
四.内存分配策略
对象优先在Eden分配:大多数情况下,对象在新生代Eden区中分配。当Eden区没有足够空间进行分配时,虚拟机将发起一次Minor GC,此时对象会进如survivor区,当对象满足一些条件后会进入老年代.
三种方式进入老年代:1.年龄增加到一定程度(默认为15岁),就将会被晋升到老年代中,对象晋升老年代的年龄阈值,可以通过参数-XX:MaxTenuringThreshold设置。。2.Survivor空间中相同年龄所有对象大小的总和大于Survivor空间的一半,年龄大于或等于该年龄的对象就可以直接进入老年代 3.大对象直接进入老年代,PretenureSizeThreshold参数,令大于这个设置值的对象直接在老年代分配
空间分配担保:在发生Minor GC之前,虚拟机会先检查老年代最大可用的连续空间是否大于新生代所有对象总空间,如果这个条件成立,那么Minor GC可以确保是安全的。
垃圾回收器:parnew (用于新生代,复制算法)和 cms收集器(老年代,标记清除算法)。