【Java Jvm工作原理 全面 】简单理解


(接着JVM工作原理(一),继续更新JVM的内容)

一、详解 新生代和老年代

(一)新生代

在这里插入图片描述

  • java堆可以分为新生代和老年代,默认创建的对象都是先放在新生代,当gc收集发生之后,若该对象没有没回收,并且达到了老年代的年龄,就被转移到老年代。
  • 一般占据堆的1/3空间。由于频繁创建对象,所以新生代会频繁触发MinorGC进行垃圾回收。
    新生代又分为 Eden区、SurvivorFrom、ServivorTo三个区。
  • Eden区: Java新对象的出生地,当Eden区内存不够的时候就会触发MinorGC,对新生代区进行一次垃圾回收。
    SurvivorTo:保留了一次MinorGC过程中的幸存者。
    SurvivorFrom:上一次GC的幸存者,作为这一次GC的被扫描者。
  • MinorGC的过程:MinorGC采用复制算法。首先,把Eden和SurvivorFrom区域中存活的对象复制到SurvicorTo区域然后,清空Eden和SurvicorFrom中的对象;最后,SurvicorTo和SurvicorFrom互换,原SurvicorTo成为下一次GC时的SurvicorFrom区。
    注意:IBM研究发现新生代对象98%都是“朝生夕灭”的,所以Eden和两块Survivor三块区域内存比例为:8:1:1,采用复制算法90%的内存我们是可用的!
(二)老年代
  • 大对象直接进入老年代
    什么是大对象?
    回答:所谓大对象就是指,需要连续的大量内存的对象,最典型的就是:很长的字符串及数组。所以大对象对虚拟机内存的分配是一个坏消息,还有更坏的消息就是:java虚拟机遇到一群“朝生夕灭”的“短命大对象”,因为经常出现大对象容易导致内存还有不少空间就提前触发垃圾回收以获取足够的空间来“安置”它们。
  • 长期存活的对象进入老年代
    有人会问多久算长期?
    回答:虚拟机给每个对象都有年龄:age 一个的计数器;假设对象在Eden出生并进行第一次Minor GC后仍存活,并且能被Survicor容纳,对象进入到Survicor区域,将对行年龄设为:1。对象在Survicor区域每熬过一次Minor GC,年龄就+1,当年龄增加到一定程度(默认15岁),就会进入老年代。
  • 动态对象年龄判断
    为了更好的适应不同的内存情况,并不是非要上面说的,当对象达到一定年龄才可以进入老年代。
    现要求:如果Survicor空间中相同年龄所有对象大小的总和大于等于Survicor空间的一半,年龄大于或者等于该年龄的对象直接进入老年代。
  • Minor GC 和Full GC 有什么不一样
    Minor GC :发生在新生代的垃圾回收动作,因为java对象大多都“朝生夕灭”,所以Minor GC操作很频繁,一般回收速度也快。
    Full GC:发生在老年代的GC,经常会伴随至少一次的Minor GC,Full GC速度会比Minor GC慢10倍以上。

二、类文件结构(Class类)

(一)无关性基石——字节码文件
  • 作为java学习者,我们知道知道java有一个很出名的宣传口号:”一次编译,处处运行“,
    及就是跨平台使用,sun公司和其它虚拟机提供商发布许多可以不同平台的虚拟机,这些虚拟机可以载入和执行同一平台的字节码文件,口号不再是口号。
  • 各种不同平台的虚拟机和所有平台都遵循着统一的程序存储格式,那就是字节码,字节码就是构成平台无关性的基石,使用java编译可以把java代码编译成存储字码的Class文件
  • java语言的各种变量,关键字和运算符的语义最终都是由多条字节码命令组合而成,因此字节码命令所提供的语义描述能力远比java代码语言本身更强大
(二) Class类文件结构
  • Class文件是一组以8字节为基础的二进制流,** 中间没有任何添加符,这使得Class文件存储的几乎全部是程序运行的必要数据,当遇到大于8个字节的空间数据时,按照高位在上的方式分割若干个8字节存储
(1)Class结构两种数据类型
  • 采用类似于C语言结构体的伪结构来存储,这种结构只有两种数据类型:无符号位和表
(1.1)无符号位
  • 无符号位属于基本数据类型,用u1,2,u4,u8分别代表:1,2,4,8字节的无符号位数,无符号可以用来代表:数字,索引引用,数量值或者uft-8编码的字符串
(1.2)表
  • 表是多个无符号数或其它表作为数据项的复合数据类型,所有表习惯性的以”_info"结尾,表用于描述有层次关系的数据结构,整个Class的实质就是一张表
    在这里插入图片描述
(2)魔数和Class版本

每个Class文件的前四个字节称为:魔数,唯一作用是识别这个文件是否可以是被虚拟机接受的Class文件,第5和第6个字节是次版本号,第7和8字节是主版本号
在这里插入图片描述

(3)常量池
  • 紧接着主次版本之后的就是常量池入口,常量池是Class文件结构中和其他项目关联最多的数据类型,也是占用空间内存最大的数据项目之一,同时它还是在Class文件中第一个出现的表类型的数据项目
  • 由于常量池中常量的数量是不固定的,所以在常量池入口需要放置一项:u2类型的数据,代表常量池容量计数器。与java语言习惯不一样,这个容量计数从1开始的,例如:下图
    在这里插入图片描述常量池容量为十六进制数:0x0016,十进制为:22,这就说明容量池有21项常量,将第0项常量空出来为了:满足后面某些指向常量池的索引值的数据在特定情况下需要表达:不引用任何一常量池项目
  • 常量池主要存放两大类常量:字面量和符号引用。字面量近似于java语言的常量概念,如:文本字符串、final声明的常量值;而符号用用则属于:编译方面原理,包含三类常量:类和接口的全限定名、字段和描述符、方法和描述符
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值