金三银四面试题(一):JVM类加载与垃圾回收

面试过程中最经典的一题:

请你讲讲在JVM中类的加载过程以及垃圾回收?

加载过程

当Java虚拟机(JVM)启动时,它会通过类加载器(ClassLoader)加载Java类到内存中。类加载是Java程序运行的重要组成部分,它负责将字节码文件加载到内存,并将其转换为运行时的Java类。

  1. 加载(Loading): 通过类的完全限定名,查找此类字节码文件,利用字节码文件创建Class 对象.

  2. 链接(Linking) 分为三个阶段:验证(Verification)、准备(Preparation)、解析(Resolution)。

    • 验证阶段确保加载的类符合Java语言规范,不会危害JVM的安全。验证包括文件格式验证、元数据验证、字节码验证和符号引用验证
    • 在准备阶段,为类的静态变量分配内存空间,并将其初始化为默认值。这些静态变量会在方法区中分配内存空间,但不会为其赋予初始值,初始值在后面的初始化阶段进行赋值。
    • 解析阶段是将类、接口、字段和方法的符号引用解析为直接引用的过程。这个过程可能包括将常量池中的符号引用替换为直接引用、对类和接口的全限定名进行解析等。
  3. 初始化(Initialization):在初始化阶段,JVM会执行类构造器()方法,该方法是由编译器自动收集类中的所有类变量的赋值动作和静态语句块(static{}块)中的语句合并产生的。JVM会保证类的初始化是线程安全的,即只会执行一次。在这个阶段,静态变量会被赋予初始值,静态代码块会被执行。

加载机制

双亲委派机制(Parent Delegation Model)是Java类加载器(ClassLoader)的一种工作机制。在Java中,类加载器按照一种树形结构层级来组织,每个类加载器都有一个父类加载器。当一个类加载器需要加载一个类时,它首先会委派给其父加载器去尝试加载,只有在父加载器无法加载该类的情况下,才会由子加载器尝试加载。这种加载方式称为双亲委派机制。

优点

  • 避免重复加载: 通过委派给父加载器,可以避免在不同的类加载器中重复加载同一个类,从而节省内存和系统资源。

  • 安全性: 通过双亲委派机制,系统类库通常由引导类加载器加载,而用户自定义的类通常由应用程序类加载器加载,这样可以有效地保护系统核心类不受用户篡改。

  • 层级管理: 可以通过双亲委派机制有效地管理类加载器的层级结构,保证类的加载顺序和一致性。

图解加载机制

分代回收

分代垃圾回收机制是一种优化垃圾回收效率的策略,它将内存分为不同的代,并根据对象的生命周期将对象分配到不同的代中,以实现更高效的内存回收。

分代垃圾回收

分代垃圾回收机制将堆内存划分为几个不同的代,通常是新生代(Young Generation)、老年代(Old Generation)和永久代(PermGen,JDK 7及以前版本)。其中,新生代用于存放刚刚被创建的对象,老年代用于存放生存时间较长的对象,永久代(在 JDK 8 中被元数据区(Metaspace)取代)用于存放类的元数据信息。

分代垃圾回收的主要思想是根据对象的生命周期来进行优化。通常情况下,大部分对象的生命周期都很短暂,它们很快就会变成垃圾。因此,分代垃圾回收机制将堆内存划分为一个较大的新生代和一个较小的老年代。新生代采用复制算法进行垃圾回收,而老年代采用标记-清除算法或标记-整理算法进行垃圾回收。

新生代垃圾回收

新生代采用了复制算法进行垃圾回收。新生代被划分为一个较大的 Eden 区和两个较小的 Survivor 区(通常称为 From 区和 To 区)。当新对象被创建时,它们被分配到 Eden 区。当 Eden 区满时,触发 Minor GC(新生代垃圾回收)。在 Minor GC 过程中,存活的对象将被复制到 To 区,然后清空 Eden 区和 From 区,并将 To 区与 From 区交换角色。这个过程称为清除(Clear)和复制(Copy)。在多次 Minor GC 后,仍然存活的对象会被晋升到老年代中。

老年代垃圾回收

老年代主要用于存放生命周期较长的对象。它采用了标记-清除算法或标记-整理算法进行垃圾回收。在老年代垃圾回收过程中,首先标记所有存活的对象,然后清除未标记的对象。在标记-清除算法中,清除后会产生内存碎片;而在标记-整理算法中,存活的对象会被整理到一端,从而减少内存碎片的产生。尽管Full GC 发生的次数不会有 Minor GC 那么频繁,但是做一次 Full GC 要比进行一次 Minor GC 的时间更长。(有的面试官还会问什么情况下会full gc?不仅仅要想到堆空间不足的情况,还有 System.gc() 这个函数)

上图仅仅是一个示意图, SO,S1的角色每轮会互换。

而且各个分区比例可以通过JVM参数进行调整。默认情况下, 新生代和老年代的比例为1:2。S0:S1:Eden = 1:1:8

回收算法

在面试经常问到的两个问题就是如何标记和如何清除

如何标记:

  1. 引用计数法(Reference Counting)是一种垃圾回收算法,其基本思想是为每个对象维护一个引用计数器,用于记录当前对象被引用的次数。当引用计数器减少到零时,说明该对象不再被任何其他对象引用,即成为垃圾对象,可以被回收。

当然这并不理想,因为会出现循环引用。所以引出第二个算法:

  1. 可达性分析(Reachability Analysis)是一种垃圾回收算法中常用的技术。它用于确定在堆内存中哪些对象是“可达”的,即哪些对象可以被程序的根节点(通常是全局变量、活动线程栈上的对象等)直接或间接引用到。基于可达性分析,垃圾收集器可以识别出不再被任何可达对象引用的对象,并将其标记为可回收的垃圾对象。

清除算法

  1. G1 算法

    JDK9之后默认的垃圾回收算法,特点保持高回收率的同时减少停顿.采用每次只清理一部分,而不是清理全部的增量式清理,以保证停顿时间不会过长

    其取消了年轻带与老年代的物理划分,但仍属于分代收集器,算法将堆分为若干个逻辑区域(region),一部分用作年轻带,一部分用作老年代,还有用来存储巨型对象的分区.和CMS相同,会遍历所有对象,标记引用情况,清除对象后会对区域进行复制移动,以整合碎片空间.

    年轻带回收:并行复制采用复制算法,并行收集,会 StopTheWorld.

    老年代回收:会对年轻带一并回收

    初始标记完成堆 root 对象的标记,会 StopTheWorld.并发标记 GC 线程和应用线程并发执行. 最终标记 完成三色标记周期,会 StopTheWorld.复制/清除会优先对可回收空间加大的区域进行回收。

  2. ZGC 算法

针对大堆内存设计,可以处理 TB 级别的堆,可以做到 10ms 以下
的回收停 顿时间.

特点:

  • 着色指针
  • 读屏障
  • 并发处理
  • 基于 region
  • 内存压缩(整理)

roots标记:标记 root 对象,会StopTheWorld.并发标记:利用读屏障与应用线程一起运行标记,可能会发生 StopTheWorld.清除会清理标记为不可用的对象. roots 重定位:是对存活的对象进行移动,以 腾出大块内存空间,减少碎片产生.重定位最开始会 StopTheWorld,取决于重定位集与对象总活动集的比例. 并发重定位与并发标记类似.

总结

JVM的类加载过程和垃圾回收是面试中几乎必问的问题,作为八股文中最经典的存在,大家一定要熟记,最好刻在DNA中。

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/778622.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

python(一)网络爬取

在爬取网页信息时,需要注意网页爬虫规范文件robots.txt eg:csdn的爬虫规范文件 csdn.net/robots.txt User-agent: 下面的Disallow规则适用于所有爬虫(即所有用户代理)。星号*是一个通配符,表示“所有”。 Disallow&…

Scikit-Learn K近邻分类

Scikit-Learn K近邻分类 1、K近邻分类1.1、K近邻分类及原理1.2、超参数K1.3、K近邻分类的优缺点2、Scikit-Learn K近邻分类2.1、Scikit-Learn K近邻分类API2.2、K近邻分类实践(鸢尾花分类)2.3、交叉验证寻找最佳K2.4、K近邻分类与Pipeline1、K近邻分类 K近邻是一种常用的分类…

JSP基础

一、JSP JSP(全称:Java Server Pages):Java 服务端页面。是一种动态的网页技术,其中既可以定义 HTML、JS、CSS等静态内容,还可以定义 Java代码的动态内容,也就是 JSP HTML Java 。如下就是js…

【NOI】树的初步认识

文章目录 前言一、树1.什么是树?2.树的基本概念3.树的基本术语3.1 节点3.1.1 根节点3.1.2 父节点、子节点3.1.3 兄弟节点、堂兄弟节点3.1.4 祖先节点、子孙节点3.1.5 叶子节点/终端节点3.1.6 分支节点/非终端节点 3.2 边3.3 度3.3.1 树的度 3.4 层次3.4.1 树的深度3…

ERROR: No matching distribution found for tb-nightly

问题描述 安装tb-lightly失败:ERROR: No matching distribution found for tb-nightly 解决方案 因为我的镜像源默认是清华的,但是pip源中没有对应的“tb-nightly”依赖包。 如果不知道的,也可以查看一下pip的配置: python -m …

【Go】结构体中Tag标识

https://blog.csdn.net/weixin_45193103/article/details/123876319 https://blog.csdn.net/qq_49723651/article/details/122005291 https://juejin.cn/post/7005465902804123679 学一点,整一点,基本都是综合别人的,弄成我能理解的内容 Tag定…

GeoTrust SSL证书有什么优势?

GeoTrust SSL证书具备以下显著优势: 1. 市场占有率比较高:GeoTrust作为知名的SSL证书供应商,拥有广泛的市场接受度和高占有率,表明其产品受到众多企业和网站的信任和采用。 2. 品牌信誉与信任标识:在高安全性浏览器中&…

Unity3d使用Jenkins自动化打包(Windows)(一)

文章目录 前言一、安装JDK二、安装Jenkins三、Jenkins插件安装和使用基础操作 实战一基础操作 实战二 四、离线安装总结 前言 本篇旨在介绍基础的安装和操作流程,只需完成一次即可。后面的篇章将深入探讨如何利用Jenkins为Unity项目进行打包。 一、安装JDK 1、进入…

在word中显示Euclid Math One公式的问题及解决(latex公式,无需插件)

问题:想要在word中显示形如latex中的花体字母 网上大多解决办法是安装Euclid Math One。安装后发现单独的符号插入可行,但是公式中选择该字体时依然显示默认字体。 解决办法:插入公式后,勾选左上角的latex 在公式块中键入latex代码…

Go语言爬虫实战(线程池)

Go语言爬虫实战 目标 利用go语言爬取指定网站的图片。实现爬取网站任意页面所有所需的图片。实现使用go语言线程池开启多个线程爬取图片内容。最后实现创建多个文件夹存储图片。 爬取网站图片 步骤 对指定URL发去GET请求,获取对应的响应。 resp, err : http.Get(…

【JavaWeb】Day24.Web入门——HTTP协议(一)

HTTP协议——概述 1.介绍 HTTP:Hyper Text Transfer Protocol(超文本传输协议),规定了浏览器与服务器之间数据传输的规则。 http是互联网上应用最为广泛的一种网络协议http协议要求:浏览器在向服务器发送请求数据时,或是服务器在…

AI写作的力量:让你的文章焕发生机

在当今数字化时代,内容创作变得越来越重要。无论是博客文章、广告文案还是社交媒体更新,优质的文本都能吸引读者的注意力并传达信息。然而,创作过程并不总是轻松的,尤其是当我们面临灵感枯竭或时间紧迫的挑战时。这就是AI写作的力…

网站为什么要选择使用安全加速SCDN?

安全加速SCDN(安全内容交付网络)是一种网络加速服务,旨在提高网站和应用程序的性能和安全性。它使用专门的技术和基础设施来加速内容传输并保护网站免受网络攻击。 安全加速SCDN可以通过内容缓存、快速传输和动态路由技术来加速网站和应用程…

安卓调试桥ADB

Logcat 命令行工具 | Android Studio | Android Developers 什么是ADB ADB 全称为 Android Debug Bridge ,是 Android SDK (安卓的开发工具)中的一个工具,起到调试桥的作用,是一个 客户端 - 服务器端程序 。其中 …

【Linux】开始掌握进程控制吧

送给大家一句话: 我并不期待人生可以一直过得很顺利,但我希望碰到人生难关的时候,自己可以是它的对手。—— 加缪 开始学习进程控制 1 前言2 进程创建2.1 fork函数初识2.2 fork函数返回值2.3 写时拷贝2.4 fork常规用法2.5 fork调用失败的原因…

3月23日笔记

广播域与泛洪范围是相同的 广播:在同一个泛洪范围内,强迫交换机泛洪(主动) 泛洪(被动) ARP的工作原理:ARP先通过广播发送请求包,所有收到该广播包的设备都会将其中的源IP和源MAC相…

Oracle存数字精度问题number、binary_double、binary_float类型

--表1 score是number(10,5)类型 create table TEST1 (score number(10,5) ); --表2 score是binary_double类型 create table TEST2 (score binary_double ); --表3 score是binary_float类型 create table TEST3 (score binary_float );实验一:分别往三张表插入 小数…

OpenCV 形态学处理函数

四、形态学处理(膨胀,腐蚀,开闭运算)_getstructuringelement()函数作用-CSDN博客 数字图像处理(c opencv):形态学图像处理-morphologyEx函数实现腐蚀膨胀、开闭运算、击中-击不中变换、形态学梯度、顶帽黑帽变换 - 知乎…

JAVA面试八股文之集合

JAVA集合相关 集合?说一说Java提供的常见集合?hashmap的key可以为null嘛?hashMap线程是否安全, 如果不安全, 如何解决?HashSet和TreeSet?ArrayList底层是如何实现的?ArrayList listnew ArrayList(10)中的li…

Day24:私信列表、私信详情、发送私信

测试用户:用户名aaa 密码aaa 查询当前用户的会话列表;每个会话只显示一条最新的私信;支持分页显示。 首先看下表结构: conversation_id: 用from_id和to_id拼接,小的放前面去(因为两个人的对话应该在一个会…