当前位置: 首页 > news >正文

JAVA面试题大全(十八)

1、说一下 jvm 的主要组成部分?及其作用?

  • 类加载器(ClassLoader)
  • 运行时数据区(Runtime Data Area)
  • 执行引擎(Execution Engine)
  • 本地库接口(Native Interface)

组件的作用: 首先通过类加载器(ClassLoader)会把 Java 代码转换成字节码,运行时数据区(Runtime Data Area)再把字节码加载到内存中,而字节码文件只是 JVM 的一套指令集规范,并不能直接交给底层操作系统去执行,因此需要特定的命令解析器执行引擎(Execution Engine),将字节码翻译成底层系统指令,再交由 CPU 去执行,而这个过程中需要调用其他语言的本地库接口(Native Interface)来实现整个程序的功能。

2、说一下 jvm 运行时数据区域?

JVM 运行时数据区域可以分为以下几个部分:

  1. 程序计数器:当前线程所执行的字节码的行号指示器。
  2. Java 虚拟机栈:描述的是 Java 方法执行的内存模型,每个方法在执行的同时都会创建一个栈帧用于存储局部变量表、操作数栈、动态链接、方法出口等信息。
  3. 本地方法栈:与虚拟机栈所发挥的作用是非常相似的,其区别只是虚拟机栈为虚拟机执行 Java 方法服务,而本地方法栈则为虚拟机使用到的 Native 方法服务。
  4. :Java 堆是 Java 虚拟机所管理的内存中最大的一块。Java 堆是被所有线程共享的一块内存区域,在虚拟机启动时创建。此内存区域的唯一目的就是存放对象实例,几乎所有的对象实例都在这里分配内存。
  5. 方法区:用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。

3、 说一下堆栈的区别?

  • 栈内存存储的是局部变量;堆内存存储的是实体;
  • 栈内存的更新速度要快于堆内存,因为局部变量的生命周期很短;
  • 栈内存存放的变量生命周期一旦结束就会被释放,而堆内存存放的实体会被垃圾回收机制不定时的回收。

4、队列和栈是什么?有什么区别? 

在 JVM(Java 虚拟机)中,队列(Queue)和栈(Stack)是两种常见的数据结构。

队列是一种先进先出(First-In-First-Out,FIFO)的数据结构。它类似于排队,新元素从队列的尾部添加,而元素从队列的头部移除。队列常用于需要按照顺序处理元素的场景,例如任务队列、消息队列等。

栈是一种后进先出(Last-In-First-Out,LIFO)的数据结构。它类似于一叠盘子,新元素总是添加到栈的顶部,而元素总是从栈的顶部移除。栈常用于函数调用、表达式求值等需要后进先出顺序的操作。

以下是队列和栈的一些主要区别:

  1. 数据访问顺序:队列按照先进先出的顺序访问元素,而栈按照后进先出的顺序访问元素。
  2. 添加和删除元素:在队列中,元素从尾部添加,从头部删除;在栈中,元素总是在顶部添加和删除。
  3. 应用场景:队列适用于需要按照顺序处理元素的情况,例如排队、任务调度等;栈适用于需要后进先出顺序的操作,例如函数调用、表达式求值等。
  4. 空间管理:队列的空间可以动态扩展,当队列已满时,可以增加队列的容量;栈的空间通常是固定的,当栈满时会发生栈溢出错误。

在 JVM 中,队列和栈的具体实现可能因不同的 JVM 实现而有所差异。例如,Java 中的Queue接口和Stack类分别提供了队列和栈的基本功能。此外,JVM 还可能使用内部的数据结构来实现队列和栈,以提高性能和效率。

5、什么是双亲委派模型? 

双亲委派模型是 Java 中的一种类加载机制,用于确保类的加载过程的安全性和正确性。

在双亲委派模型中,类加载器被组织成一个层次结构,从顶部到底部依次是启动类加载器、扩展类加载器和应用程序类加载器。当一个类需要被加载时,JVM 会首先将加载请求委派给父类加载器,如果父类加载器无法找到或加载该类,则再由子类加载器尝试加载。

双亲委派模型的主要优点包括:

  1. 安全性:可以避免用户自定义的类覆盖 Java 核心类库中的类,从而保证了 Java 平台的安全性。
  2. 一致性:可以确保同一个类在不同的类加载器中都是同一个实例,从而保证了类的一致性。
  3. 可扩展性:可以方便地实现类的热部署和热替换,从而提高了系统的可扩展性。

总之,双亲委派模型是 Java 中非常重要的一个机制,它保证了类的加载过程的安全性、正确性和一致性。

6、说一下类加载的执行过程?

在 Java 中,类加载的执行过程主要包括以下几个阶段:

  1. 加载:将类的二进制数据从指定的源(如磁盘文件、网络连接等)读取到内存中,并创建一个代表该类的Class对象。
  2. 验证:验证类的字节码是否符合 Java 虚拟机的规范,确保类的正确性和安全性。这一阶段主要包括检查类的结构、语法、语义等。
  3. 准备:为类的静态变量分配内存,并设置默认初始值。这些静态变量将在类的初始化阶段被赋值。
  4. 解析:将类中的符号引用转换为直接引用,以便在运行时能够正确地访问对象的方法和属性。
  5. 初始化:执行类的初始化代码,包括静态变量的赋值和静态代码块的执行。这是类加载的最后一个阶段,也是类真正开始执行的阶段。

需要注意的是,类加载的执行过程是由 Java 虚拟机自动完成的,开发人员通常不需要直接干预。但是,在某些情况下,例如需要动态加载类或实现自定义类加载器时,开发人员可能需要了解类加载的机制和过程。

 7、怎么判断对象是否可以被回收?

  • 引用计数器:为每个对象创建一个引用计数,有对象引用时计数器 +1,引用被释放时计数 -1,当计数器为 0 时就可以被回收。它有一个缺点不能解决循环引用的问题;
  • 可达性分析:从 GC Roots 开始向下搜索,搜索所走过的路径称为引用链。当一个对象到 GC Roots 没有任何引用链相连时,则证明此对象是可以被回收的。 

8、java 中都有哪些引用类型? 

在 Java 中,有以下几种引用类型:

  1. 强引用(Strong Reference):这是最常见的引用类型。当一个对象被强引用引用时,垃圾回收器不会回收该对象,直到所有对该对象的强引用都被删除。
  2. 软引用(Soft Reference):软引用用于描述一些还有用但并非必需的对象。在系统内存不足时,垃圾回收器会回收软引用对象。
  3. 弱引用(Weak Reference):弱引用也是用于描述非必需的对象。与软引用不同的是,垃圾回收器会更积极地回收弱引用对象,只要垃圾回收器发现弱引用对象,就会将其回收。
  4. 虚引用(Phantom Reference):虚引用主要用于跟踪对象的垃圾回收状态。它不能单独使用,必须与引用队列(ReferenceQueue)一起使用。当垃圾回收器准备回收一个对象时,会将该对象的虚引用加入到引用队列中。

9、说一下 jvm 有哪些垃圾回收算法? 

  • 标记-清除算法:只回收,不整理
  • 标记-整理算法:标记-清楚算法的优化,解决了内存碎片的问题
  • 复制算法:解决内存碎片
  • 分代回收算法(常用):年轻代以复制为主,老年代以标记-整理为主

10、详细介绍一下 CMS 垃圾回收器? 

CMS(Concurrent Mark-Sweep),是以牺牲吞吐量为代价来获得最短回收停顿时间的垃圾回收器。对于要求服务器响应速度的应用上,这种垃圾回收器非常适合。在启动 JVM 的参数加上“-XX:+UseConcMarkSweepGC”来指定使用 CMS 垃圾回收器。

CMS 使用的是标记-清除算法,所以在 gc 的时候会产生大量的内存碎片,当剩余内存不能满足程序运行要求时,系统将会出现 Concurrent Mode Failure,临时 CMS 会采用 Serial Old 回收器进行垃圾清除,此时的性能将会被降低。

11、新生代垃圾回收器和老年代垃圾回收器都有哪些?有什么区别?

新生代回收器:Serial、ParNew、Parallel Scavenge
老年代回收器:Serial Old、Parallel Old、CMS
整堆回收器:G1

新生代垃圾回收器一般采用的是复制算法。复制算法的优点是效率高,缺点是内存利用率低;

老年代垃圾回收器一般采用的是标记-整理算法。

12、说一下 jvm 有哪些垃圾回收器?

  • Serial:最早的单线程串行垃圾回收器,新生代垃圾回收器,使用复制算法。
  • Serial Old:Serial 垃圾回收器的老年版本,同样也是单线程的,可以作为 CMS 垃圾回收器的备选预案,老年代垃圾回收器,使用标记-整理算法。
  • ParNew:是 Serial 的多线程版本,新生代垃圾回收器,使用复制算法。
  • Parallel 和 ParNew 收集器类似是多线程的,但 Parallel 吞吐量优先,可以牺牲等待时间换取系统的吞吐量,新生代垃圾回收器,使用复制算法。
  • Parallel Old 是 Parallel 老年版本,Parallel 使用的是复制算法,Parallel Old 使用的是标记-整理的内存回收算法,是老年代垃圾回收器。
  • CMS:一种以获得最短停顿时间为目标的收集器,非常适用 B/S 系统,老年代垃圾回收器,使用标记-清除算法。
  • G1:一种兼顾吞吐量和停顿时间的 GC 实现,是 JDK 9 以后的默认 GC 选项,是整堆回收器,使用标记-整理算法。

13、简述分代垃圾回收器是怎么工作的? 

分代回收器有两个分区:老生代和新生代。

新生代的默认空间是 1/3,老生代的默认占比是 2/3。

新生代使用的是复制算法,新生代里有 3 个分区:Eden、To Survivor、From Survivor,它们的默认占比是 8:1:1,它的执行流程如下:

把 Eden + From Survivor 存活的对象放入 To Survivor 区;
清空 Eden 和 From Survivor 分区;
From Survivor 和 To Survivor 分区交换,From Survivor 变 To Survivor,To Survivor 变 From Survivor。

每次在 From Survivor 到 To Survivor 移动时都存活的对象,年龄就 +1,当年龄到达 15(默认配置是 15)时,升级为老生代。大对象也会直接进入老生代。

老生代当空间占用到达某个值之后就会触发全局垃圾收回,一般使用标记整理的执行算法。以上这些循环往复就构成了整个分代垃圾回收的整体执行流程。

14、说一下 jvm 调优的工具?

JDK 自带了很多监控工具,都位于 JDK 的 bin 目录下,其中最常用的是 jconsole 和 jvisualvm 这两款视图监控工具。

  • jconsole:用于对 JVM 中的内存、线程和类等进行监控;
  • jvisualvm:JDK 自带的全能分析工具,可以分析:内存快照、线程快照、程序死锁、监控内存的变化、gc 变化等。

15、常用的 jvm 调优的参数都有哪些? 

-Xms2g:初始化堆大小为 2g;
-Xmx2g:堆最大内存为 2g;
-XX:NewRatio=4:设置年轻代和老年代的内存比例为 1:4;
-XX:SurvivorRatio=8:设置新生代 Eden 和 Survivor 比例为 8:2;
–XX:+UseParNewGC:指定使用 ParNew + Serial Old 垃圾回收器组合;
-XX:+UseParallelOldGC:指定使用 ParNew + ParNew Old 垃圾回收器组合;
-XX:+UseConcMarkSweepGC:指定使用 CMS + Serial Old 垃圾回收器组合;
-XX:+PrintGC:开启打印 gc 信息;
-XX:+PrintGCDetails:打印 gc 详细信息。

 16、内存溢出、内存泄露、GC的基本概念

内存溢出:out of memory,是指程序在申请内存时,没有足够的内存空间供其使用,出现out of memory;比如申请了一个integer,但给它存了long才能存下的数,那就是内存溢出。

内存泄露:memory leak,是指程序在申请内存后,无法释放已申请的内存空间,一次内存泄露危害可以忽略,但内存泄露堆积后果很严重,无论多少内存,迟早会被占光。其实说白了就是该内存空间使用完毕之后未回收。

gc分为full gc 跟 minor gc(Young GC也就是Minor GC),当每一块区满的时候都会引发gc。
 

相关文章:

JAVA面试题大全(十八)

1、说一下 jvm 的主要组成部分?及其作用? 类加载器(ClassLoader)运行时数据区(Runtime Data Area)执行引擎(Execution Engine)本地库接口(Native Interface)…...

如何利用Firebase Hosting来托管网站

文章目录 如何利用Firebase Hosting来托管网站前提条件详细步骤1. 安装 Firebase CLI2. 登录 Firebase3. 初始化 Firebase 项目4. 准备网站文件5. 部署到 Firebase6. 配置自定义域名(可选) 常见问题 如何利用Firebase Hosting来托管网站 以下是更详细的…...

揭秘“循环消费”模式:消费即收益,购物新体验

亲爱的朋友们,大家好,我是李华。今天,我要为大家介绍一种正在悄然兴起的商业模式——“循环消费”。你是否曾想过,在消费的同时,还能获得额外的收益和回馈?这种新型模式正在逐渐改变我们的购物体验。 近期&…...

图片怎样在线改像素大小?电脑快速修改图片大小的方法

在设计图片的时候下载的图片尺寸一般会比较大,在网上使用经常会因为尺寸的问题导致无法正常上传,那么如何快速在线改图片大小呢?想要修改图片尺寸可以在直接选择网上的图片改大小工具的功能来快速完成修改,操作简单方便使用&#…...

SELINUX=enforcing时无法启动httpd服务的解决方案(semanage命令以及setroubleshoot-server插件的妙用)

一、问题描述: 当/etc/selinux/conf被要求必须是SELINUXenforcing,不被允许使用setenforce 0宽松模式 我们启动httpd就会报错: Job for httpd.service failed because the control process exited with error code. See "systemctl s…...

【C++】list的使用方法和模拟实现

❤️欢迎来到我的博客❤️ 前言 list是可以在常数范围内在任意位置进行插入和删除的序列式容器,并且该容器可以前后双向迭代list的底层是双向链表结构,双向链表中每个元素存储在互不相关的独立节点中,在节点中通过指针指向其前一个元素和后…...

【物联网实战项目】STM32C8T6+esp8266/mqtt+dht11+onenet+uniapp

一、实物图 前端uniapp效果图(实现与onenet同步更新数据) 首先要确定接线图和接线顺序: 1、stm32c8t6开发板连接stlinkv2下载线 ST-LINK V2STM323.3V3.3VSWDIOSWIOSWCLKSWCLKGNDGND 2、ch340串口连接底座(注意RXD和TXD的连接方式…...

Pyhton 二叉树层级遍历

class TreeNode:def __init__(self, val0, leftNone, rightNone):self.val valself.left leftself.right rightclass Solution:def levelOrder(self, root: Optional[TreeNode]) -> List[List[int]]:res []# 空节点,直接返回if not root:return resque [roo…...

Flutter 中的 FadeTransition 小部件:全面指南

Flutter 中的 FadeTransition 小部件:全面指南 在 Flutter 中,动画是一种吸引用户注意力并提供流畅用户体验的强大工具。FadeTransition 是 Flutter 提供的一个动画小部件,它允许子组件在不透明度上进行渐变,从而实现淡入和淡出效…...

缓存存储器:性能提升的关键

目录 基本原理 主存与缓存的地址映射 主存的替换策略 缓存的写操作策略 Pentium 4 的缓存组织 使用多级缓存减少缺失损失 结论 在计算机系统中,缓存存储器(Cache Memory)发挥着至关重要的作用。它充当处理器和主存之间的高速缓冲区&am…...

『大模型笔记』工程师的LLMs简介!

💡工程师的LLMs简介 ! 文章目录 1. Embeddings Conceptually(嵌入的概念)1.1. One-hot Encodings(独热编码)1.2. Embeddings(嵌入)2. LLM Basics(LLM 基础知识)3. Autoregressive LLMs(自回归LLMs)4. Where to go from here(何去何从?)5. 参考文献https://devo…...

Vue中的常用指令

Vue 会根据不同的【指令】,针对标签实现不同的【功能】 概念:指令(Directives)是 Vue 提供的带有 v- 前缀 的 特殊 标签属性。 为啥要学:提高程序员操作 DOM 的效率。 vue 中的指令按照不同的用途可以分为如下 6 大…...

百度页面奔跑的白熊html、css

一、相关知识-动画 1.基本使用:先定义再调用 2. 调用动画 用keyframes定义动画(类似定义类选择器) keyframes动画名称{ 0%{ width:100px; } 100%{ width:200px; } } 使用动画 div { width:200px; height:200px; background-…...

Day-02面向对象

一、匿名函数 和函数的作用一致,都是进行代码逻辑的封装, 区别1 在定义时,匿名函数可以不指定函数的名字 区别2 匿名函数执行实现简单的计算 区别3 匿名函数会自动将计算的结果返回 定义格式 lambda 参数1,参数2...:计算逻辑(参数的处理逻辑…...

Sentinel-2 哨兵二号数据介绍及下载

1 Sentinel-2简介 SENTINEL-2 is a European wide-swath, high-resolution, multi-spectral imaging mission. Sentinel-2 是高分辨率多光谱成像卫星,一颗卫星的重访周期为10天,两颗互补,重访周期为5天。分为2A和2B两颗卫星。2A于2015年6月…...

阿里智能信息数据挖掘复盘

(嘻嘻——不嘻嘻) 挫败呜呜呜,钉钉忘装,还要手机登录,迟到三分钟。 一上来就问项目,没有自我介绍。 第一篇的重要特征是什么直接忘记,正负样本比,过拟合的判断标准,特…...

Flutter中图片是怎么在flutter上呈现出来的?

在Flutter中,图片的呈现是通过使用Image组件来实现的。Image组件是一个用于加载和显示图片的Widget,可以从本地文件、网络URL或内存中加载图片,并在应用界面上进行渲染。 图片在Flutter中的呈现过程如下: 加载图片: 使…...

使用 CNN 训练自己的数据集

CNN(练习数据集) 1.导包:2.导入数据集:3. 使用image_dataset_from_directory()将数据加载tf.data.Dataset中:4. 查看数据集中的一部分图像,以及它们对应的标签:5.迭代数据集 train_ds&#xff0…...

自动控制: 最小二乘估计(LSE)、加权最小二乘估计(WLS)和线性最小方差估计

自动控制: 最小二乘估计(LSE)、加权最小二乘估计(WLS)和线性最小方差估计 在数据分析和机器学习中,参数估计是一个关键步骤。最小二乘估计(LSE)、加权最小二乘估计(WLS&…...

基于VMware安装Linux虚拟机

1.准备Linux环境 首先,我们要准备一个Linux的系统,成本最低的方式就是在本地安装一台虚拟机。为了统一学习环境,不管是使用MacOS还是Windows系统的同学,都建议安装一台虚拟机。 windows采用VMware,Mac则采用Fusion …...

XML Group端口详解

在XML数据映射过程中,经常需要对数据进行分组聚合操作。例如,当处理包含多个物料明细的XML文件时,可能需要将相同物料号的明细归为一组,或对相同物料号的数量进行求和计算。传统实现方式通常需要编写脚本代码,增加了开…...

C++实现分布式网络通信框架RPC(3)--rpc调用端

目录 一、前言 二、UserServiceRpc_Stub 三、 CallMethod方法的重写 头文件 实现 四、rpc调用端的调用 实现 五、 google::protobuf::RpcController *controller 头文件 实现 六、总结 一、前言 在前边的文章中,我们已经大致实现了rpc服务端的各项功能代…...

无法与IP建立连接,未能下载VSCode服务器

如题,在远程连接服务器的时候突然遇到了这个提示。 查阅了一圈,发现是VSCode版本自动更新惹的祸!!! 在VSCode的帮助->关于这里发现前几天VSCode自动更新了,我的版本号变成了1.100.3 才导致了远程连接出…...

可靠性+灵活性:电力载波技术在楼宇自控中的核心价值

可靠性灵活性:电力载波技术在楼宇自控中的核心价值 在智能楼宇的自动化控制中,电力载波技术(PLC)凭借其独特的优势,正成为构建高效、稳定、灵活系统的核心解决方案。它利用现有电力线路传输数据,无需额外布…...

pam_env.so模块配置解析

在PAM(Pluggable Authentication Modules)配置中, /etc/pam.d/su 文件相关配置含义如下: 配置解析 auth required pam_env.so1. 字段分解 字段值说明模块类型auth认证类模块,负责验证用户身份&am…...

数据链路层的主要功能是什么

数据链路层(OSI模型第2层)的核心功能是在相邻网络节点(如交换机、主机)间提供可靠的数据帧传输服务,主要职责包括: 🔑 核心功能详解: 帧封装与解封装 封装: 将网络层下发…...

优选算法第十二讲:队列 + 宽搜 优先级队列

优选算法第十二讲:队列 宽搜 && 优先级队列 1.N叉树的层序遍历2.二叉树的锯齿型层序遍历3.二叉树最大宽度4.在每个树行中找最大值5.优先级队列 -- 最后一块石头的重量6.数据流中的第K大元素7.前K个高频单词8.数据流的中位数 1.N叉树的层序遍历 2.二叉树的锯…...

Unity | AmplifyShaderEditor插件基础(第七集:平面波动shader)

目录 一、👋🏻前言 二、😈sinx波动的基本原理 三、😈波动起来 1.sinx节点介绍 2.vertexPosition 3.集成Vector3 a.节点Append b.连起来 4.波动起来 a.波动的原理 b.时间节点 c.sinx的处理 四、🌊波动优化…...

浪潮交换机配置track检测实现高速公路收费网络主备切换NQA

浪潮交换机track配置 项目背景高速网络拓扑网络情况分析通信线路收费网络路由 收费汇聚交换机相应配置收费汇聚track配置 项目背景 在实施省内一条高速公路时遇到的需求,本次涉及的主要是收费汇聚交换机的配置,浪潮网络设备在高速项目很少,通…...

c++第七天 继承与派生2

这一篇文章主要内容是 派生类构造函数与析构函数 在派生类中重写基类成员 以及多继承 第一部分:派生类构造函数与析构函数 当创建一个派生类对象时,基类成员是如何初始化的? 1.当派生类对象创建的时候,基类成员的初始化顺序 …...