JVM入门

文章目录JVM一、阶段梳理1.1 番外资料1.2 编译流程二、JVM2.1 知识点整理2.2 运行时的数据结构程序计数器虚拟机栈本地方法栈堆区方法区运行时常量池直接内存2.3 垃圾回收对象的回收判断算法垃圾收集算法垃圾收集器2.x 对象三、排障工具的使用3.1 概括故障处理工具基础工具安全工具国际化远程方法调用Corba部署工具3.2 JVisualVM && Graalvm3.3 JProfiler四、字节码文件与类加载4.1 Class类文件结构4.2 字节码指令4.3 类的生命周期4.
摘要由CSDN通过智能技术生成

JVM

文章目录
基于《深入理解Java虚拟机:JVM高级特性与最佳实践(第3版)》

目前主要针对OpenJDK及OracleJDK的HotSpot虚拟机进行学习

一、阶段梳理

针对学习路径的一个概括性梳理

1.1 番外资料

文章目录
Java虚拟机(JVM)面试题(2020最新版)_ThinkWon的博客
/
JVM速成手册 | IT宅-arthinking’s blog

1.2 编译流程

(1)Java源文件 👉(2)编译 👉 (3)生成class字节码文件 👉(4) JVM加载类

后续的笔记目录也将根据这套流程进行深入分析

二、JVM

2.1 知识点整理

  1. JVM运行时候的数据结构
  2. 对象的出生过程
  3. 为对象实例分配内存的方式
  4. 垃圾回收算法及机制

2.2 运行时的数据结构

来看另外一组图

程序计数器

线程私有 生命周期同线程相同

字节码文件的行号解释器,通过它指定由哪一行代码运行,同样可以实现循环、跳转

但是这是线程私有的,在多线程环境下每个线程执行的字节码文件行号是不一样的

虚拟机栈

线程私有 生命周期同线程相同

字面上看,它是一个栈的数据结构

  1. 每个方法被执行的时候,虚拟机会同步创建一个栈帧
  2. 栈帧存放了 局部变量表、操作数栈、动态链接、方法出口等信息
  3. 调用时入栈,用完出栈
文章目录
运行时栈帧结构_xtayfjpk的专栏-CSDN博客
本地方法栈

线程私有 生命周期同线程相同

运行非Java的Native方法,例如fork线程

堆区

基本作用

  1. 存放对象实例
  2. 受GC堆管理
  3. 其中又有新生代老年代的说法
文章目录
Java中的新生代、老年代、永久代和各种GC 博客园 (cnblogs.com)
方法区
  1. 存储已被加载的类型信息、常量、静态变量等
  2. 原先永久代使用JVM的内存,现在替换成元空间使用本地内存
  3. Jdk 8后方法区的字符串常量池给了堆区
运行时常量池
文章目录
java虚拟机:运行时常量池 - xiaotian15 - 博客园 (cnblogs.com)
直接内存

直接内存并不属于JVM的内存结构,它是物理机的内存,但是JVM虚拟机可以调用该部分内存

文章目录
JVM中的直接内存_麦田里的守望者-CSDN博客

后期有空的时候要通过做实验观察一下JDK17

2.3 垃圾回收

对象的出生到死亡,从类加载到GC的回收的心路历程

对象的回收判断算法
  1. 引用计数算法
  2. 可达性分析算法
  3. 引用链判断
垃圾收集算法
  1. 清除算法
  2. 复制算法
  3. 整理算法
垃圾收集器
文章目录
Jvm垃圾回收器(终结篇) - 不二尘 - 博客园 (cnblogs.com)

2.4 JVM的参数设置

文章目录
JVM系列三:JVM参数设置、分析 - redcreen - 博客园 (cnblogs.com)

2.5 堆内存快照

可以用JProfiler进行分析

2.6 Java对象实例结构

对象头、对象体、对齐字节

对象头

对象体

对齐字节

2.7 JVM对象访问

  • 句柄访问

    如果使用句柄访问的话,那么Java堆中将会划分出一块内存来作为句柄池,reference中存储的就是对象的句柄地址,而句柄中包含了对象实例数据与类型数据各自的具体地址信息

  • 直接指针

    使用直接指针访问,那么Java堆对象的布局中就必须考虑如何放置访问类型数据的相关信息,而reference中存储的直接就是对象地址

这2中对象的访问方式各有优势,使用句柄访问方式的最大好处就是reference中存储的是稳定的句柄地址。

而使用直接指针的最大好处就是速度更快。

三、排障工具的使用

3.1 概括

故障处理工具

基础工具

安全工具

国际化

远程方法调用

Corba

java IDL、RMI-IIOP

部署工具

3.2 JVisualVM && Graalvm

Graalvm-ce-java8-21.2.0

相当于把JDK中基本的排障工具进行组合,更加方便的一个可视化工具

跟Jconsole差不多,但是它可以引入插件

3.3 JProfiler

贵死了,正版授权499美元

可以用来分析DUMP日志

四、字节码文件与类加载

描述类文件结构/类加载

4.1 Class类文件结构

  • 魔数

    每个Class头4个字节被称为魔数,用来确定这个文件是不是能被JVM虚拟机接受的类文件

    例如这个文件存储的版本号魔数是B,但是JVM只能执行A版本的Class文件

  • 常量池

    字面量 and 符号引用

  • 访问标志

    说明这类的信息,例如:是否是public,是否是接口,是否是final

  • 索引、属性、方法、字段等

4.2 字节码指令

通过将指令放在虚拟机操作数栈,指令执行进行入栈和出栈

4.3 类的生命周期

4.4 类的加载过程

加载
  1. 通过类的全限定名来获取定义这个类的二进制流
  2. 把字节流静态存储结构,转换为,方法区数据结构,通过类加载器加载到方法区中
  3. 在内存生成这个类的Class对象,作为方法区这个类的各种数据访问入口
验证

连接阶段的第一步,验证字节流中的信息是否符合规范

准备

为类中定义的变量(静态变量)分配内存,这些变量所使用的内存都在方法区进行分配

解析

JVM将常量池内的符号引用替换为直接引用的过程

直接引用的实现跟虚拟机的内存布局相关,直接引用是可以直接指向目标的指针

初始化

4.5 类加载器

public abstract class ClassLoader

类加载器直接决定了比较两个类是否“相等”,由不同类加载器加载的类是必然不相等的

例如通过应用类加载器和自定义类加载器加载同一个类,equal()方法出来都不会相同

双亲委派模型的工作过程

  1. 如果一个类加载器收到了类加载请求,它首先不会自己去加载,而是抛给父类加载器,层层往上抛,跑到老祖宗加载器
  2. 类加载是通过类的全限定名进行加载的,如果父类加载器在它搜索范围内没有这个类,就从上往下抛给儿子加载
  3. 这么做的好处是,有一个优先级的层次关系,并且如果过多的类加载器加载的类不会显得混乱
  4. 类加载请求的前提是,会先判断这个类有没有被加载过

4.6 破坏双亲委派模型&&线程上下文类加载器

文章目录
(14条消息) 双亲委派模型与线程上下文类加载器_Rico’s Blogs-CSDN博客

五、字节码执行引擎

文章目录
深入理解JVM字节码执行引擎_疯一样的女子-CSDN博客

六、前端编译优化 && 后端编译优化

1

我裂开,不是我现阶段该学的东西

1

over

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值