热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

java复制对象_Java面试JVM

来源:segmentfault.comujack3021JVM篇1.JVM垃圾回收的时候如何确定垃圾?是否知道什么是GCRoots?GCroots就是一

3a23baffc6429d3eced7920ca86354db.png

来源:segmentfault.com/u/jack3021

JVM篇

6efcf1ed24d4073e98ee36e2579ab3ad.png

1.JVM垃圾回收的时候如何确定垃圾?是否知道什么是GC Roots?

GC roots就是一组必须活跃的引用

java使用了可达性分析的方法来判断对象是否是垃圾。

基本思路就是从GC Roots对象作为起点向下搜索,如果一个对象到GC Roots没有任何的引用链时候,则说明对象不可用。5d070940c8093012b3bc679ca59e8384.png852090a809b2161771fd5ed6eb3ae1a5.png

2. 可以作为GC Roots的对象有哪些?

虚拟机栈。方法区中的类静态属性的对象。方法区中常量引用的对象。本地方法栈中native方法引用的对象。

3.如何盘点查看JVM系统默认值

  • Boolean类型 公式:-XX:+或者-某个属性值 +代表开启 -代表关闭 例子:jinfo -flag PrintGCDetails 端口 -XX:-PrintGCDetails

  • KV设值类型 公式:-XX:属性key=属性值value 例子:-XX:MetaspaceSize=128m

java -XX:+PrintFlagsInitial 查看初始值 java -XX:+PrintFlagsFinal 查看最终值

4.如何在运行java命令时候,同时打印参数

java -XX:+PrintFlagsFinal -XX:MetaspaceSize=512m 运行类名


30897da8fe96fd1c1819e8dbd4e3849e.png

5f51edad16c89dff69b1d09ae5e745fb.png

c05d4d8a3d13123405643cb66d345ef2.png

5.新生代转移到老年代的触发条件

  1. 长期存活的对象。

  2. 大对象直接进入老年代。

  3. 在年轻代GC后仍然放不下的对象。

  4. 动态年龄判断 ,大于等于某个年龄的对象超过了survivor空间一半。

6.什么时候发生YoungGC和FulGC

  • Eden 空间占满了, 会触发 Young GC

  • Minor(Scavenge) GC 后仍然存活的对象会被复制到 S0 (survivor 0)中去。这样 Eden 就被清空可以分配给新的对象。又触发了一次 Minor GC,

    S0 和 Eden 中存活的对象被复制到 S1 中, 并且 S0和 Eden 被清空。在同一时刻, 只有 Eden 和一个 Survivor Space 同时被操作。当每次对象从 Eden 复制到 Survivor Space 或者从 Survivor Space 中的一个复制到另外一个, 有一个计数器会自动增加值。默认情况下如果复制发生超过 15.次, JVM 会停止复制并把他们移到老年代中去. 同样的如果一个对象不能在 Eden 中被创建, 它会直接被创建在老年代中。

  • FulGC :

    • a) 老年代(Tenured)被写满;

    • b) 元空间满;

    • System.gc()被显示调用;

    • 上一次GC之后Heap的各域分配策略动态变化。

7.类加载过程是什么?

类的加载分为 加载、链接 (包括验证、准备、解析三步)、初始化。

  • 加载是文件到内存的过程。通过类的完全限定名查找此类字节码文件,并利用字节码文件创建一个Class对象。

  • 验证是否符合虚拟机要求,保证不会危害虚拟机自身安全,包含四种:文件格式验证,元数据验证,字节码验证,符号引用验证。

    准备阶段是进行内存分配。为类变量也就是类中由static修饰的变量分配内存,并且设置初始值,这里要注意,初始值是0或者null,而不是代码中设置的具体值,代码中设置的值是在初始化阶段完成的。另外这里也不包含用final修饰的静态变量,因为final在编译的时候就会分配了。

    解析主要是解析字段、接口、方法。主要是将常量池中的符号引用替换为直接引用的过程。直接引用就是直接指向目标的指针、相对偏移量等。

  • 初始化就是完成对静态块和静态变量赋值。

74714859305f2784f9f12bde5a49e155.png

8.对象的加载过程?

①类加载检查: 虚拟机遇到一条 new 指令时,首先将去检查这个指令的参数是否能在常量池中定位到这个类的符号引用,并且检查这个符号引用代表的类是否已被加载过、解析和初始化过。如果没有,那必须先执行相应的类加载过程。

举个例子,我们的string就算是对象创建,既是 String str= new String("abc");  首先也会在常量池中定位是否存在值。若不存在,则会在常量池也建立一个abc.

②分配内存: 在类加载检查通过后,接下来虚拟机将为新生对象分配内存。对象所需的内存大小在类加载完成后便可确定,为对象分配空间的任务等同于把一块确定大小的内存从 Java 堆中划分出来。分配方式有 “指针碰撞” 和 “空闲列表” 两种,选择那种分配方式由 Java 堆是否规整决定,而Java堆是否规整又由所采用的垃圾收集器是否带有压缩整理功能决定。

③初始化零值: 内存分配完成后,虚拟机需要将分配到的内存空间都初始化为零值(不包括对象头),这一步操作保证了对象的实例字段在 Java 代码中可以不赋初始值就直接使用,程序能访问到这些字段的数据类型所对应的零值。

④设置对象头: 初始化零值完成之后,虚拟机要对对象进行必要的设置,例如这个对象是那个类的实例、如何才能找到类的元数据信息、对象的哈希吗、对象的 GC 分代年龄等信息。 这些信息存放在对象头中。 另外,根据虚拟机当前运行状态的不同,如是否启用偏向锁等,对象头会有不同的设置方式。

⑤执行 init 方法: 在上面工作都完成之后,从虚拟机的视角来看,一个新的对象已经产生了,但从 Java 程序的视角来看,对象创建才刚开始, 方法还没有执行,所有的字段都还为零。所以一般来说,执行 new 指令之后会接着执行  方法,把对象按照程序员的意愿进行初始化,这样一个真正可用的对象才算完全产生出来。

9.GC垃圾回收四大算法?

  1. 引用计数法

    a486c29e78e7985c3444c750440474d0.png

  2. 复制算法

    年轻代中Minor GC使用的就是复制算法。

    88ea40051886d0369cd347f08c132c20.png

  3. 标记清除(Mark-Sweep)

    老年代 一般是由标记清除,或者是标记清除和标记整理实现。

    先扫描需要被回收的对象,然后标记起来,进行整体清除。

    优点:不需要额外的空间。

    缺点:会造成内存碎片。

  4. 标记压缩(Mark-Compact)

    老年代 一般是由标记清除,或者是标记清除和标记整理实现。

    722981e47e18aac73dfc5027ab53aa81.png

    7c41dec131adba6cf2029a6bef95e5e1.png

    serial 串行垃圾回收器 :它为单线程环境设置且只使用一个线程进行垃圾回收,会暂停所有用户线程。不适于用服务器。

    Parallel 并行垃圾回收器:多个垃圾收集线程并行工作,此时用户线程是暂停的,适用于弱交互场景。

    CMS 并发标记清除 :用户线程和垃圾收集线程同时执行,不一定是并行也可能是交替执行。适用于对响应时间有要求的场景。

    10.怎么查看默认的垃圾收集器是哪个?

    java -XX:+PrintCommandLineFlags -version

    11. 串行垃圾回收器:Serial

    只使用一个线程进行垃圾回收,会暂停所有用户线程。是java虚拟机运行在32位client模式下的默认新生代垃圾收集器。fcba4e912f951be0355ff604ed0a3dbd.png
    优点:简单高效。
    缺点:需要暂停其他线程。
    对应的JVM参数是-XX:+UseSerialGC
    开启后就会在Young区和Old区使用。
    新生代使用的是复制算法,老年代使用的是标记整理(压缩)算法。

    12. ParNew(并行)收集器

    使用多线程进行垃圾回收,在垃圾收集时,会Stop-The-World暂停其他所有工作线程直到他收集结束。84723fa9f51afb879ff79e62348c1edb.png
    ParNew收集器其实就是Serial新生代的多线程版本老年代还是单线程。
    对应的JVM参数是-XX:+UseParNewGC
    开启后只影响新生代的收集,不影响老年代。
    新生代使用的是复制算法,老年代使用的是标记整理(压缩)算法。

    13. Parallel Scavenge 并行收集器

    是一个新生代的垃圾收集器,使用的是复制算法。
    在新生代和老年代都是并行化。6c0d9fe24b161becb334dec92012f016.png
    JDK8使用的就是 Parallel + Parallel Old 收集器
    UseParallelGC 即 Parallel Scavenge 和 Parallel Old。
    对应的JVM参数是-XX:+UseParallelGC 或者 -XX:+UseParallelOldGC
    开启该参数后:新生代使用的是复制算法,老年代使用的是标记整理(压缩)算法。

    14. CMS 收集器(Concurrent Mark Sweep:并发标记清除)

    是一种以获取最短回收停顿时间为目标的收集器。e991df4843f146c5735aef85eb53a850.png
    并发收集低停顿,可以和用户线程一起执行。
    对应的JVM参数是-XX:+UseConcMarkSweepGC 开启后自动将-XX:+UseParNewGC打开。
    使用ParNew(Young区)+CMS(Old区)+ Serial Old收集器组合,Serial Old 将作为CMS出错的后备收集器。
    CMS的四步过程:

  • 初始标记 :只是标记一下GC Roots能关联的对象,速度很快,仍然需要暂停其他线程。

  • 并发标记:进行GC Roots跟踪的过程,和用户线程一起工作,不需要暂停其他线程。主要标记全部对象。

  • 重新标记:为了修改在并发标记期间,发生变动的对象,进行重新标记,需要暂停所有线程。

  • 并发清除:清除GC Roots中不可达的对象,不需要暂停其他线程。

优点:并发收集低停顿
缺点:并发执行,对CPU资源压力大。采用的是标记清除算法,会产生内存碎片。

## 15. G1 收集器

是一个可以在年轻代和老年代一起使用的垃圾收集器,可以并发执行,设计的目的是为了代替CMS收集器
G1采用的是标记整理(压缩)算法,局部是通过复制算法,不会产生内存碎片。
优点:

  • G1是一个有整理内存过程的垃圾收集器,不会产生很多内存碎片。

  • G1的STW更可控,在停顿时间上增加了预测机制,用户可以指定期望停顿的时间。

  • 将内存划分为多个独立的子区域,其内部在小范围内还是要进行年轻代和老年代的区分。

底层原理:

  • 每个块的大小为1MB-32MB,最多有2048个区域。

  • 如果有大对象,默认直接分配到老年代,G1划分了一个Humongous区来存放,如果一个H区不够的话,会找连续的H区来存放。为了能找到连续的H区,有时候不得不Full GC。

## 16. 生产环境如果CPU过高,怎么定位?

先用top命令查看cpu占比最高的,然后用jps来查看是那一个后台进程。

jps -l

然后使用

ps - mp 进程ID -o THREAD,tid,time

5a1425566cc5a6a070f08269f137df33.png
查看是具体哪个线程占比最高。
然后使用

printf "%x\n" 线程ID

得到转换后的16进制格式 小写。
然后使用

jstack 进程ID | grep 线程id -A60

## 17.什么是双亲委派机制?

java虚拟机对class文件采用的是按需加载,只有当需要用到的时候才会加载到内存生成class对象,采用的是双亲委派机制,把请求交给父类处理。是一种任务委派模式。
优点:

  • 避免类的重复加载。

  • 避免核心API被篡改。76b8ac373e23eebe841fe5530d377644.png271502e1e5ea1cbb99d9c8a43a871291.pngd0fc28e76e8f28c62bbe233082f6edd5.png

更多精彩?

在公众号对话框输入以下关键词查看更多优质内容!大数据 | Java | 1024 | 电子书 | 速查表 Python进阶 | 面试 | 手册 | 成神 | 思想 小程序命令行人工智能软件测试Web前端Python

b5fe430d5f7702695543dfbe32a6b187.png

扫码关注我们

获取更多学习资料

视频 | 面试 | 技术 | 电子书 

程序员编程:javaje

小编微信:BW22266688

我知道你“在看”

2d0084a7d5efe7ed639ae21499c1a3ff.gif



推荐阅读
  • 本文详细介绍了SQL日志收缩的方法,包括截断日志和删除不需要的旧日志记录。通过备份日志和使用DBCC SHRINKFILE命令可以实现日志的收缩。同时,还介绍了截断日志的原理和注意事项,包括不能截断事务日志的活动部分和MinLSN的确定方法。通过本文的方法,可以有效减小逻辑日志的大小,提高数据库的性能。 ... [详细]
  • 如何搭建Java开发环境并开发WinCE项目
    本文介绍了如何搭建Java开发环境并开发WinCE项目,包括搭建开发环境的步骤和获取SDK的几种方式。同时还解答了一些关于WinCE开发的常见问题。通过阅读本文,您将了解如何使用Java进行嵌入式开发,并能够顺利开发WinCE应用程序。 ... [详细]
  • Nginx使用AWStats日志分析的步骤及注意事项
    本文介绍了在Centos7操作系统上使用Nginx和AWStats进行日志分析的步骤和注意事项。通过AWStats可以统计网站的访问量、IP地址、操作系统、浏览器等信息,并提供精确到每月、每日、每小时的数据。在部署AWStats之前需要确认服务器上已经安装了Perl环境,并进行DNS解析。 ... [详细]
  • 在Docker中,将主机目录挂载到容器中作为volume使用时,常常会遇到文件权限问题。这是因为容器内外的UID不同所导致的。本文介绍了解决这个问题的方法,包括使用gosu和suexec工具以及在Dockerfile中配置volume的权限。通过这些方法,可以避免在使用Docker时出现无写权限的情况。 ... [详细]
  • Commit1ced2a7433ea8937a1b260ea65d708f32ca7c95eintroduceda+Clonetraitboundtom ... [详细]
  • Android中高级面试必知必会,积累总结
    本文介绍了Android中高级面试的必知必会内容,并总结了相关经验。文章指出,如今的Android市场对开发人员的要求更高,需要更专业的人才。同时,文章还给出了针对Android岗位的职责和要求,并提供了简历突出的建议。 ... [详细]
  • [译]技术公司十年经验的职场生涯回顾
    本文是一位在技术公司工作十年的职场人士对自己职业生涯的总结回顾。她的职业规划与众不同,令人深思又有趣。其中涉及到的内容有机器学习、创新创业以及引用了女性主义者在TED演讲中的部分讲义。文章表达了对职业生涯的愿望和希望,认为人类有能力不断改善自己。 ... [详细]
  • 如何用UE4制作2D游戏文档——计算篇
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了如何用UE4制作2D游戏文档——计算篇相关的知识,希望对你有一定的参考价值。 ... [详细]
  • JVM 学习总结(三)——对象存活判定算法的两种实现
    本文介绍了垃圾收集器在回收堆内存前确定对象存活的两种算法:引用计数算法和可达性分析算法。引用计数算法通过计数器判定对象是否存活,虽然简单高效,但无法解决循环引用的问题;可达性分析算法通过判断对象是否可达来确定存活对象,是主流的Java虚拟机内存管理算法。 ... [详细]
  • XML介绍与使用的概述及标签规则
    本文介绍了XML的基本概念和用途,包括XML的可扩展性和标签的自定义特性。同时还详细解释了XML标签的规则,包括标签的尖括号和合法标识符的组成,标签必须成对出现的原则以及特殊标签的使用方法。通过本文的阅读,读者可以对XML的基本知识有一个全面的了解。 ... [详细]
  • 本文介绍了RPC框架Thrift的安装环境变量配置与第一个实例,讲解了RPC的概念以及如何解决跨语言、c++客户端、web服务端、远程调用等需求。Thrift开发方便上手快,性能和稳定性也不错,适合初学者学习和使用。 ... [详细]
  • 本文介绍了三种方法来实现在Win7系统中显示桌面的快捷方式,包括使用任务栏快速启动栏、运行命令和自己创建快捷方式的方法。具体操作步骤详细说明,并提供了保存图标的路径,方便以后使用。 ... [详细]
  • 本文介绍了在使用Python中的aiohttp模块模拟服务器时出现的连接失败问题,并提供了相应的解决方法。文章中详细说明了出错的代码以及相关的软件版本和环境信息,同时也提到了相关的警告信息和函数的替代方案。通过阅读本文,读者可以了解到如何解决Python连接服务器失败的问题,并对aiohttp模块有更深入的了解。 ... [详细]
  • Java在运行已编译完成的类时,是通过java虚拟机来装载和执行的,java虚拟机通过操作系统命令JAVA_HOMEbinjava–option来启 ... [详细]
  • 本文介绍了一种轻巧方便的工具——集算器,通过使用集算器可以将文本日志变成结构化数据,然后可以使用SQL式查询。集算器利用集算语言的优点,将日志内容结构化为数据表结构,SPL支持直接对结构化的文件进行SQL查询,不再需要安装配置第三方数据库软件。本文还详细介绍了具体的实施过程。 ... [详细]
author-avatar
丿虚伪丿
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有