面试题-JVM

什么情况下会发生栈内存溢出

描述栈定义,再描述为什么会溢出,再说明一下相关配置参数,OK的话可以给面试官手写是一个栈溢出的demo。
  1. 栈是线程私有的,他的生命周期与线程相同,每个方法在执行的时候都会创建一个栈帧,用来存储局部变量表,操作数栈,动态链接,方法出口等信息。局部变量表又包含基本数据类型,对象引用类型
  2. 如果线程请求的栈深度大于虚拟机所允许的最大深度,将抛出StackOverflowError异常,方法递归调用产生这种结果
  3. 如果Java虚拟机栈可以动态扩展,并且扩展的动作已经尝试过,但是无法申请到足够的内存去完成扩展,或者在新建立线程的时候没有足够的内存去创建对应的虚拟机栈,那么Java虚拟机将抛出一个OutOfMemory 异常。(线程启动过多)
  4. 参数 -Xss 去调整JVM栈的大小

详解JVM内存模型

思路: 给面试官画一下JVM内存模型图,并描述每个模块的定义,作用,以及可能会存在的问题,如栈溢出等。

image.png

  1. 程序计数器:当前线程所执行的字节码的行号指示器,用于记录正在执行的虚拟机字节指令地址,线程私有。
  2. Java虚拟栈:存放基本数据类型、对象的引用、方法出口等,线程私有。
  3. Native方法栈:和虚拟栈相似,只不过它服务于Native方法,线程私有。
  4. Java堆:java内存最大的一块,所有对象实例、数组都存放在java堆,GC回收的地方,线程共享。
  5. 方法区:存放已被加载的类信息、常量、静态变量、即时编译器编译后的代码数据等。(即永久带),回收目标主要是常量池的回收和类型的卸载,各线程共享

JVM内存为什么要分成新生代,老年代,持久代。新生代中为什么要分为Eden和Survivor。

思路: 先讲一下JAVA堆,新生代的划分,再谈谈它们之间的转化,相互之间一些参数的配置(如: –XX:NewRatio,–XX:SurvivorRatio等),再解释为什么要这样划分,最好加一点自己的理解

共享内存区划分

  1. 共享内存区 = 持久带 + 堆
  2. 持久带 = 方法区 + 其他
  3. Java堆 = 老年代 + 新生代
  4. 新生代 = Eden + S0 + S1

一些参数的配置

  • 默认,新生代与老年代的比例的值是1:2,可以通过参数-XX:NewRatio配置。
  • 默认,Edem:from:to=8:1:1(可以通过参数-XX:SurvivorRatio来设定)
  • Survivor区中的对象被复制次数(对应虚拟机参数-XX:+MaxTenuringThreshold)

为什么要分为Eden和Survivor?为什么要设置两个Survivor区?

  1. 如果没有Survivor,Eden区每进行一次Minor GC,存活的对象就会被送到老年代。老年代很快被填满,触发Major GC.老年代的内存空间远大于新生代,进行一次Full GC消耗的时间比Minor GC长得多,所以需要分为Eden和Survivor。
  2. Survivor的存在意义,就是减少被送到老年代的对象,进而减少Full GC的发生,Survivor的预筛选保证,只有尽力了16次Minor GC还能在新生代中存活的对象,才会被送到老年代。
  3. 设置两个Survior区最大的好处就是解决了碎片化,刚刚新建的对象在Eden中,经历一次Minor GC,Eden中的存活对象就会被移到到第一块survivor space S0,Eden被清空;等Eden区在满了,就再触发一次Minor GC,Eden和S0中的存活对象又被复制送入第二块survivor space S1(这个过程非常重要,因为这种复制算法保证了s1中来自S0和Eden两部分的存活对象占有连续的内存空间,避免了碎片化的发生。)

JVM中一次完整的GC流程是怎样的,对象如何晋升到老年代

思路:先描述一下Java堆内存划分,再解释Minor GC、Major GC、full GC、以及他们之间的转化流程
  1. Java堆 = 老年代 + 新生代
  2. 新生代 = Eden + S0 + S1
  3. 当Eden区的空间满了,Java虚拟机会触发一次Minor GC,以收集新生代的垃圾,存活下来的对象,则会转移到Survivor区。
  4. 大对象(需要大量连续内存空间的Java对象,如那种很长的字符串)则直接进入老年态。
  5. 如果对象在Eden出生,并经过第一次Minor GC后仍然存活,并且被Survivor容纳的话,年龄设为1,每熬过一次Minor GC,年龄+1,若年龄超过一定限制(15),则被晋升到老年态。即上期存活的指向进入老年态。
  6. 老年代满了而无法容纳更多的对象,Minor GC之后通常就进行Full GC,Full GC清理整个内存堆-包括年轻代和年老代。
  7. Major Gc发生在老年代的GC,清理老年区,经常会伴随至少一次Minor GC,比Minor GC慢10倍以上。

你知道哪几种垃圾收集器,各自的优缺点,重点讲下CMS和G1,包括原理,流程,优缺点

思路: 一定要记住典型的垃圾收集器,尤其cms和G1,它们的原理与区别,涉及的垃圾回收算法。

几种垃圾收集器

  1. Serial收集器: 单线程的收集器,收集垃圾时,必须stop the world,使用复制算法。
  2. ParNew收集器: Serial收集器的多线程版本,也需要stop the world,复制算法
  3. Parallel Scavenge收集器: 新生代收集器,复制算法的收集器,并发的多线程收集器,目标是达到一个可控的吞吐量。如果虚拟机总共运行100分钟,其中垃圾花掉1分钟,吞吐量就是99%。
15 声望
3 粉丝
0 条评论
推荐阅读
【已结束】SegmentFault 思否面试闯关挑战赛!
“金三银四”求职季到啦,能力自查与提升迫在眉睫🔥 社区专栏与技术问答联合推出: SegmentFault 思否面试闯关挑战赛 本期挑战赛于 3 月 7 日 正式开赛,共设四重关卡,不限技术方向。快来和小伙伴们一起主动追击,...

SegmentFault思否14阅读 13.7k评论 17

封面图
疫情已过,2023 我的前端面试记录
顺利入职。把我最近找工作的心得记录下来。工作交接确定 lastday整理手头工作,相关对接人、交接人放文档中工作交接过渡阶段。做好被咨询者,该拉人拉人,该拉群拉群平时沟通顺畅的同事如果没有 WX 可以加一个属...

linong11阅读 1.1k

简历上的项目,需要这样描述才有亮点!
每每准备面试,总有些小伙子甩出自己的豆包项目,不是Xxx管理系统,就是某某自动化平台。就像这几年自己的经历都放在 CRUD 编写上了,走的那是加班的道,干的都是体力的活。

小傅哥4阅读 1.2k

封面图
记一次旁观他人的技术面试
最近没有什么面试经历,上一次面试已经是将近一年前了,所以没办法有效回忆到当时面试的状况。好在近期肉大(@meathill)有在做一个模拟面试的选题,就可以另辟蹊径写一篇旁观其他人面试的文章。

陟上晴明4阅读 961

JS核心知识点梳理——正则篇(下)
正则是一个前端必须掌握的知识。但是由于用的少,忘了记,记了忘,导致面试经常坐蜡。这里上篇先介绍正则的规则,下篇结合一些具体题目,带大家重新学习巩固一下正则,争取面试给自己加分。

Runningfyy3阅读 2.2k

消息推送平台终于要上线啦!
我的开源项目消息推送平台Austin终于要上线了,迎来在线演示的第一版!🔥项目在线演示地址:[链接]消息推送平台🔥推送下发【邮件】【短信】【微信服务号】【微信小程序】【企业微信】【钉钉】等消息类型。[链接][链...

Java3y3阅读 1.1k

js中null和undefined的区别
1,诞生时间null在前,undefined在后。因为js作者Brendan-Eich在创造js语言时,直接抄了java很多东西。也包括null,后期发现js中的null有缺陷,又创造了undefined。(《JavaScript高级程序设计》中有说,下面的不同...

天渺工作室2阅读 496

封面图
15 声望
3 粉丝
宣传栏