秋招突击——7/24——知识补充——JVM类加载机制

文章目录

    • 引言
    • 类加载机制
      • 知识点复习
        • 类的生命周期
          • 1、加载
          • 2、连接——验证
          • 3、连接——准备
          • 4、连接——解析
          • 5、初始化
        • 类加载器和类加载机制
          • 类加载器
          • 类加载机制——双亲委派模型
      • 面试题整理
        • 1、类加载是什么
        • 2、类加载的过程是什么
        • 3、有哪些类加载器?
        • 4、双亲委派模型是什么
        • 5、如何判断两个类是否相等
    • 总结

引言

  • 在百度提前批面试中,第一个章节的问题关于类加载的相关知识点,忘得一干二净,这里整理一下!
    • 主要是类加载的过程还有双亲委派模型
  • 整理也是按照之前的惯例,先是基本的知识点,然后就是对应的面试题整理

类加载机制

知识点复习

类的生命周期
  • 类的生命周期如下,除了最后的使用和卸载,其他的基本上都很重要
    • 加载
    • 连接
      • 验证
      • 准备
      • 解析
    • 初始化
    • 使用
    • 卸载
  • 特征
    • 上述生命周期是按顺序开始,但是并不是按顺序完成
    • 通常一个阶段执行的过程中调用和激活另外一个阶段

在这里插入图片描述

1、加载
  • 类加载器主要完成三件事,分别是
    • 找到在哪里:通过一个类的全限定名,来获取定义此类的二进制字节流
    • 加载到方法区:将字节流所代表的静态存储结构转化为方法区的运行时数据结构
    • 创造对象提供入口:在内存中生成一个代表这个类的java.lang.Class对象,作为方法区这个类的各种数据的访问入口

在这里插入图片描述

2、连接——验证
  • 目的
    • 检查Class字节流,确保这个字节流是符合要求的,不会有安全性问题
  • 验证内容
    • 文件格式验证:版本号,还有开头的符号
    • 元数据验证:语义分析,是否符合Java语言规范,继承抽象类的类是否实现抽象方法等
    • 字节码验证:语义分析,数据流和控制流分析,程序是否合法或者符合逻辑等
    • 符号引用验证:对类中所引用的信息的匹配性校验(常量池中的各种符号引用)
      • 根据符号引用描述的名字能否找到对应的类
      • 符号引用的对象是否可被当前类访问

从文件格式,到语法规范,再到所引用对象

3、连接——准备
  • 目的
    • 为类的**静态变量(static修饰的)**分配内存,初始化为默认值,如果使用了final修饰,则会给初始值
  • 注意
    • 只给类变量分配内存,不给实例变量分配内存
    • 使用final修饰的static变量,会直接赋初始值,不会默认值
4、连接——解析
  • 目的
    • 将常量池中符号引用替换为直接引用
      • 符号引用
        • 是一组符号来描述所引用的目标,相当于是相对引用
      • 直接引用
        • 直接指向目标的指针、相对偏移量、或者一个能定位到目标的句柄
5、初始化
  • 目的

    • 类的静态变量赋初始值,不同于之前的准备,是给静态变量赋默认值
  • 初始化方式

    • 声明类变量指定初始值
    • 使用静态代码块指定初始值
  • 步骤

    • 如果这个类没有被加载或者连接,则程序先加载和连接这个类
    • 如果该类的直接父类没有被初始化,则先初始化其直接父类
    • 如果类中有这些初始化语句,则系统依次执行这些初始化语句
  • 类初始化的时机

  • 只有当类主动使用的时候,才会导致类的初始化,具体时机如下

    • 调用对应类的静态方法
    • 初始化某一个类的子类,父类也会被初始化
    • 创建类的实例
    • 使用反射
类加载器和类加载机制
类加载器
  • 类唯一性的确立

    • 一个类必须由加载他的类加载器和这个类本身一块共同确立其唯一性
  • 具体应用

    • 同一个Class文件加载的对象,可能调用getClass返回的都是同一个名字,但是如果类的加载器不同,instanceof返回的结果也是false

三个类加载器

  • 启动类加载器

    • 负责加载Java核心类库,是所有类加载器的顶层
    • 使用本地代码实现,依赖于操作系统的本地代码C++或者C
      • 无法通过Java代码直接获取到启动类加载器的实例
    • 核心类库
      • 运行时类库:rt.jar
      • 基础类:String、Object、System
  • 扩展类加载器

    • 负责加载标准扩展目录中的类和资源。
    • 使用Java代码实现,可以获取对应对象()了解
 ClassLoader extClassLoader = appClassLoader.getParent();System.out.println("Extension ClassLoader: " + extClassLoader);
  • 应用类加载器
    • 用户自定义类和第三方库的默认类加载器,加载应用程序类路径下的类库
ClassLoader appClassLoader = ClassLoader.getSystemClassLoader();
System.out.println("Application ClassLoader: " + appClassLoader);
类加载机制——双亲委派模型

在这里插入图片描述

  • 定义
    • 如果一个类加载器的收到了类加载的请求,首先不会尝试自己去加载这个类,而是把这个请求委托给父类加载器去完成
      • 所有的类加载请求,都应该传递到最顶层的启动类加载器中。
    • 只有当父加载器反馈自己无法完成这个加载请求时,子加载器才会尝试自己去完成加载

典型应用

  • 能不能自定义类加载器加载String类?
    • 不行
      在这里插入图片描述

面试题整理

1、类加载是什么
  • 类加载就是把Class文件中的类信息加载到虚拟机中,并形成可以被虚拟机使用的Java类型是类加载机制。

  • Java的运行期间动态加载和连接:Java中类型的加载、连接和初始化是在运行期间完成的,实现了Java的动态扩展性。

  • 一个类从加载到虚拟机再到卸载需要经历如下流程

    • 加载
    • 连接
      • 验证
      • 准备
      • 解析
    • 初始化
    • 使用
    • 卸载
2、类加载的过程是什么
  • 加载

    • 通过类的全限定名,找到对应二进制字节流文件
    • 将二进制字节流文件中的类的静态存储结构加载到方法区中,转为运行时数据。
    • 在堆区创建对应的Class对象,作为访问类信息的入口
  • 验证

    • 检查字节流,防止载入错误或者恶意的字节流文件,导致JVM崩溃
    • 验证流程:文本格式验证、符号引用验证、元数据验证、字节码验证等
  • 准备

    • 为类的静态变量分配内存,并赋默认值或者常量(final static修饰的)
  • 解析

    • 将符号引用替换为直接引用,能够直接指向引用对象句柄或者指针等
  • 初始化

    • 直到该阶段,JVM才开始执行类中编写的代码,根据程序员的编码对类的静态变量去赋值,
    • 执行类构造方法中的clinit方法
3、有哪些类加载器?
  • 有三层类加载器

启动类加载器

  • 在JVM启动时创建,加载最核心的类,如Object、String等,使用本地代码,由操作系统实现

扩展类加载器

  • 扩展类加载器,复杂加载一些扩展的系统类,比如XML、加密、网络编程等功能类

应用类加载器

  • 系统类加载器,是加载用户类路径上的类库,直接在代码中使用
  • 如果没有自定义类加载器,一般情况下,默认类加载器就是应用类加载器。
    • 自定义类加载器是通过继承ClassLoader并重写findclass实现的
4、双亲委派模型是什么
  • 类加载器具有等级制度,但不是继承关系,分层但非继承,以组合的方式,复用父加载器的功能。
    • 除了顶层的启动类加载器之外,其余类加载器都要用自己的父加载器

具体原理
* 一个类加载器收到类加载请求,不会自己去加载,而是把请求委派给父加载器。以此类推,最后所有请求都会到启动类加载器。
* 只有当父类加载器无法完成式,子类加载器才会去尝试加载

5、如何判断两个类是否相等
  • 确定一个类需要类自身的信息还有对应的加载器,共同确定唯一性。
  • 两个类只有由同一个类加载器加载才有比较意义
    • 如果不是同一个类加载器加载,即使来在同一个Class文件,两个类也不相等。

总结

  • 又攻克了一个难关,好好背一下,至少保证了以后在遇到类似的题目,基本上都能过了!
  • 今天本来是想看完垃圾回收机制的,但是晚上腰太疼了,就去推拿了,然后出去吃了点东西,回来的比较晚,剩下两个半小时,要把昨天的面经整理好的,就不看垃圾回收机制了!明天做个笔试,应该也不会刷题了,后续要出去旅游,请假三天!回来接着学!

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

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

相关文章

Redis一致性与分布式锁

Redis一致性 何为redis一致性 即在项目中,redis缓存中的数据要与数据库当中的数据保持一致。 那么这里,就会有小伙伴要问了,redis缓存中的数据不就是从数据库当中查询出来的吗?怎么会不一致呢? 笔者在这里解答一下…

Unite 上海 强势回归

​​​ 他回归了 Unite 大会是一年一度的 Unity 全球开发者盛会。今年,Unite 将于 7 月盛夏点亮上海外滩。此次盛会,我们将以“团结”为核心,凝聚全球 3000 多位 Unity 社区精英的力量,共同开启 Unity 技术的新纪元。 在这里&am…

UE学习笔记--干货满满!FString 的 Equals 和 == 源码深度探析

目录 前言FString 的 operatorESearchCaseStricmpBothAsciiLowerAsciiStricmp 结论Stricmp 代码验证整理思路 前言 最近大概写了如下代码 TArray<FString> TestArray; FString Z1 "Z1", z1 "z1"; TestArray.Emplace(Z1);if(TestArray.Contains(z…

代码随想录第十七天|动态规划(1)

目录 LeetCode 509. 斐波那契数列 LeetCode 70. 爬楼梯 LeetCode 746. 使用最小花费爬楼梯 LeetCode 62. 不同路径 LeetCode 63. 不同路径 II 总结 动态规划在算法课上学习过&#xff0c;看过了之后有一些熟悉感。&#xff08;虽然贪心算法也学过&#xff0c;但是不如动态…

样式迁移及代码

一、定义 1、使用卷积神经网络&#xff0c;自动将一个图像中的风格应用在另一图像之上&#xff0c;即风格迁移&#xff1b;两张输入图像&#xff1a;一张是内容图像&#xff0c;另一张是风格图像。 2、训练一些样本使得样本在一些cnn的特征上跟样式图片很相近&#xff0c;在一…

Java字符串与Unicode编码(码点、代码单元、基本多语言平面BMP、辅助平面、代理对)

Java字符串与Unicode编码 1. Unicode编码简介 Unicode是一个为世界上所有书写系统设计的字符编码标准。它旨在解决不同编码标准之间不兼容的问题&#xff0c;使得计算机能够处理和显示世界上几乎所有的字符。Unicode为每个字符分配了一个唯一的数字&#xff0c;称为“码点”&…

字典集合案例

1.统计字符 统计字符串中每个字符出现的次数 s l like summer very much #去掉空格 s s.replace(" ","") d dict() for i in s:if i in d:d[i] 1else:d[i] 1 for i in d:print(i,d[i]) 2.求不重复的随机数 #导入随机数 import random a int(input(&q…

自动化测试的艺术:Xcode中GUI测试的全面指南

自动化测试的艺术&#xff1a;Xcode中GUI测试的全面指南 在软件开发过程中&#xff0c;图形用户界面&#xff08;GUI&#xff09;测试是确保应用质量和用户体验的关键环节。Xcode&#xff0c;作为苹果的官方集成开发环境&#xff08;IDE&#xff09;&#xff0c;提供了一套强大…

智能疲劳驾驶检测:基于YOLO和深度学习的全流程实现

引言 疲劳驾驶是导致交通事故的重要原因之一。为了提高道路安全&#xff0c;及时检测和预警驾驶员的疲劳状态显得尤为重要。本文介绍了一种基于深度学习的疲劳驾驶检测系统。该系统利用YOLO模型&#xff08;YOLOv8/v7/v6/v5&#xff09;进行疲劳驾驶检测&#xff0c;并提供了详…

OD C卷 - 密码输入检测

密码输入检测 &#xff08;100&#xff09; 给定一个密码&#xff0c;‘<’ 表示删除前一个字符&#xff0c;输出最终得到的密码&#xff0c;并判断是否满足密码安全要求&#xff1a; 密码长度>8;至少包含一个大写字母&#xff1b;至少包含一个小写字母&#xff1b;至少…

探索若依(Ruoyi):开源的企业级后台管理系统解决方案

探索若依&#xff08;Ruoyi&#xff09;&#xff1a;开源的企业级后台管理系统解决方案 在现代企业管理中&#xff0c;拥有一个高效、稳定的后台管理系统是至关重要的。若依&#xff08;Ruoyi&#xff09;作为一款开源的企业级后台管理系统&#xff0c;为企业提供了丰富的功能…

SpringBoot中JSR303校验

JSR是 Java EE 的一种标准&#xff0c;用于基于注解的对象数据验证。在Spring Boot应用中&#xff0c;你可以通过添加注解直接在POJO类中声明验证规则。这样可以确保在使用这些对象进行操作之前&#xff0c;它们满足业务规则。个人认为非常有用的&#xff0c;因为它减少了代码中…

2.6基本算法之动态规划2989:糖果

描述 由于在维护世界和平的事务中做出巨大贡献&#xff0c;Dzx被赠予糖果公司2010年5月23日当天无限量糖果免费优惠券。在这一天&#xff0c;Dzx可以从糖果公司的N件产品中任意选择若干件带回家享用。糖果公司的N件产品每件都包含数量不同的糖果。Dzx希望他选择的产品包含的糖…

被问到MQ消息已丢失,该如何处理?

在分布式系统中&#xff0c;消息中间件&#xff08;如 RabbitMQ、RocketMQ、Kafka、Pulsar 等&#xff09;扮演着关键角色&#xff0c;用于解耦生产者和消费者&#xff0c;并确保数据传输的可靠性和顺序性。尽管我们通常会采取多种措施来防止消息丢失&#xff0c;如消息持久化、…

【Vue实战教程】之 Vue Router 路由详解

Vue Router路由 1 路由基础 1.1 什么是路由 用Vue.js创建的项目是单页面应用&#xff0c;如果想要在项目中模拟出来类似于页面跳转的效果&#xff0c;就要使用路由。其实&#xff0c;我们不能只从字面的意思来理解路由&#xff0c;从字面上来看&#xff0c;很容易把路由联想…

HTML(五)——HTML区块,布局

HTML区块 HTML可以通过 <div> 和 <span>将元素组合起来&#xff0c;可以来布局&#xff0c;就是盒子&#xff0c;div是块级盒子&#xff0c;里面 可以放任何东西&#xff0c;span里面装的是文本 HTML 区块元素 大多数 HTML 元素被定义为块级元素或内联元素。 实…

Java 面试 | Redis

目录 1. 在项目中缓存是如何使用的&#xff1f;2. 为啥在项目中要用缓存&#xff1f;3. 缓存如果使用不当会造成什么后果&#xff1f;4. redis 和 memcached 有什么区别&#xff1f;5. redis 的线程模型是什么&#xff1f;6. 为什么单线程的 redis 比多线程的 memcached 效率要…

dns逆向解析,主从服务,多域名访问(穿插ntp服务器)

复习 域名解析&#xff1a; 正向解析&#xff1a;将域名解析为ip 反向解析&#xff1a;将ip解析为域名 逆向解析 关闭防火墙和selinux&#xff0c;配置静态ip [rootdns ~]# vim /etc/named.rfc1912.zones [rootdns ~]# vim /etc/named.conf [rootdns ~]# cd /var/named/ [rootd…

【电子数据取证】了解数据库

文章关键词&#xff1a;电子数据取证、数据库取证、手机取证 一、前言 数据库是信息系统中不可或缺的部分。无论是取证收集&#xff0c;网站重建又或是开发程序都离不开数据库这个角色。 可能你已经或多或少看到过像是MySQL、Redis、MongoDB之类的程序&#xff0c;这些程序统…

前端:Vue学习-4

前端&#xff1a;Vue学习-4 1. 组件缓存 keep-alive2. 状态管理工具 - Vuex2.1 vuex 提供数据&使用数据 - mapState2.2 mutations 修改数据 - mapMutations2.3 actions - 异步操作 - mapActions2.4 getters - 计算属性 - mapGetters 3. Vuex 模块 modules - state,mutation…