文档章节

谈谈对JVM的理解

o
 osc_gu9d45li
发布于 2019/04/07 17:34
字数 1718
阅读 14
收藏 0

行业解决方案、产品招募中!想赚钱就来传!>>>

        JVM可谓是学习JAVA基础中的基础了,但仍有不少同学对JVM概念还是比较模糊,甚至没有听说过,对java的理解也只是在基础语法 层面,本文就将对JVM进行初步介绍,因篇幅所限,只能介绍JVM基础,如需要进一步学习,建议阅读机械工业出版社出版的《深入理解JAVA虚拟机》。

        请尊重作者劳动成果,转载请标明原文链接:

   https://www.cnblogs.com/jpcflyer/p/10666099.html

        Java虚拟机规范中规定的JVM如下图所示:
        可以看出,JVM由JVM运行时数据区(图示中蓝色框包含部分)、执行引擎、本地库接口、本地方法库组成。
 
        JVM运行时数据区,分为线程共享部分(方法区、堆)和线程隔离区(虚拟机栈、本地方法栈和程序计数器)。
        1.方法区
         用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。
        运行时常量池(Runtime Constant Pool)是方法区的一部分。.Class文件中除了有类的版本/字段/方法/接口等描述信息外,还有一项信息是常量池(Constant Pool Table),用于存放编译期生成的各种字面量和符号引用,这部分内容将类在加载后进入方法区的运行时常量池中存放.
运行时常量区的内容并不只是在编译期间产生,通过String.intern()也可以实现在运行时向常量区中添加内容。
        需要注意的是:从JDK8开始,方法区被元数据区替代了。具体的原因和两者的区别可以参考官网。
 
        2.堆
        是JVM中最大的一块内存区域,该区域的目的只是用于存储对象实例及数组。该区域也是GC的最主要区域。
        根据Java虚拟机规范的规定,Java堆可以处于物理上不连续的内存空间中,只要逻辑上是连续的即可,就像我们的磁盘空间一样.在实现时,既可以实现固定大小的,也可以是可扩展的,不过当前主流的虚拟机都是按照可扩展来实现的(通过-Xmx和-Xms控制).如果在堆中没有内存完成实例分配,并且堆也无法再扩展时,就会抛出OutOfMemoryError异常。
 
        3.虚拟机栈
        每个线程方法在执行时都会创建一个栈帧,包含局部变量表、返回地址、操作数栈等信息。每个方法的执行与完成就对应的栈帧的入栈与出栈过程 。局部变量表占用空间的大小在编译期就确定了。这里需要注意:如果线程请求的栈深度大于虚拟机所允许的深度,将会抛出StackOverflowError异常;如果虚拟机栈可以动态扩展(当前大部分的Java虚拟机都可动态扩展,只不过Java虚拟机规范中也允许固定长度的虚拟机栈),当扩展时无法申请到足够的内存时将会抛出OutOfMemoryError异常。
 
        4.本地方法栈
        与虚拟机栈类似,不过其中执行是本地方法。对于HotSpot虚拟机而言,本地方法栈和虚拟机栈是统一的。
 
        5.程序计数器
       是一个小的内存空间,如果线程正在执行的是一个java方法,则此内存区域记录正在执行的虚拟机字节码指令的地址;如果线程正在执行的是native方法,则计算器中的值为空。此内存区域是唯一一个在JAVA虚拟机规范中没有规定任何OutOfMemoryError情况的区域。
 
        这几部分都有相关的JDK自带工具可以分析查看,比如jps, jstack, jmap, jhat, jstat等,还有图形化工具jconsole,jvisualvm,但对于Linux服务器就无能为力了。
 
        好了,关于JVM就讲完了,接下来进行提问:JVM哪些区域会发生OOME,以及各自原因是什么?
 
        堆内存不足是最常见的 OOM 原因之一,抛出的错误信息是“java.lang.OutOfMemoryError:Java heap space”,原因可能千奇百怪,例如,可能存在内存泄漏问题;也很有可能就是堆的大小不合理,比如我们要处理比较可观的数据量,但是没有显式指定 JVM 堆大小或者指定数值偏小;或者出现 JVM 处理引用不及时,导致堆积起来,内存无法释放等。
        而对于 Java 虚拟机栈和本地方法栈,这里要稍微复杂一点。如果我们写一段程序不断的进行递归调用,而且没有退出条件,就会导致不断地进行压栈。类似这种情况,JVM 实际会抛出 StackOverFlowError;当然,如果 JVM 试图去扩展栈空间的的时候失败,则会抛出 OutOfMemoryError。
        对于老版本的 Oracle JDK,因为永久代的大小是有限的,并且 JVM 对永久代垃圾回收(如,常量池回收、卸载不再需要的类型)非常不积极,所以当我们不断添加新类型的时候,永久代出现 OutOfMemoryError 也非常多见,尤其是在运行时存在大量动态类型生成的场合;类似 Intern 字符串缓存占用太多空间,也会导致 OOM 问题。对应的异常信息,会标记出来和永久代相关:“java.lang.OutOfMemoryError: PermGen space”。
        随着元数据区的引入,方法区内存已经不再那么窘迫,所以相应的 OOM 有所改观,出现 OOM,异常信息则变成了:“java.lang.OutOfMemoryError: Metaspace”。
        直接内存不足,也会导致 OOM。
 
        后记:
        JVM是JAVA面试过程中最容易被问到的基础题目,在本篇JVM介绍完后,后面还准备了更多有意思的JAVA基础面试题,这些将作为提升JAVA基础能力的免费系列课程,从面试题出发,对每个问题举一反三,以点带面,不做不求甚解之人,最终目标不是学会答题,而是学会题目本身涉及到的所有知识点。暂定的全部面试题目课程包含如下内容:
        谈谈你对JVM的理解?
        final,finally,finalize有什么区别?
        String,StringBuffer,StringBuilder有什么区别?
        Exception和Error有什么区别?
        Hashtable,HashMap,TreeMap有什么区别?
        Vector,ArrayList,LinkedList有什么区别?
        int和Integer有什么区别?
        接口和抽象类有什么区别?
        如何保证集合是线程安全的?
        谈谈你知道的设计模式?
 
        搜索关注微信公众号“程序员姜小白”,获取更新精彩内容哦。
 
o
粉丝 0
博文 500
码字总数 0
作品 0
私信 提问
加载中
请先登录后再评论。
Netty那点事(三)Channel与Pipeline

Channel是理解和使用Netty的核心。Channel的涉及内容较多,这里我使用由浅入深的介绍方法。在这篇文章中,我们主要介绍Channel部分中Pipeline实现机制。为了避免枯燥,借用一下《盗梦空间》的...

黄亿华
2013/11/24
2W
22
5分钟 maven3 快速入门指南

前提条件 你首先需要了解如何在电脑上安装软件。如果你不知道如何做到这一点,请询问你办公室,学校里的人,或花钱找人来解释这个给你。 不建议给Maven的服务邮箱来发邮件寻求支持。 安装Mav...

fanl1982
2014/01/23
1.2W
6
研究虚拟机--Jikes RVM

Jikes研究虚拟机(Jikes Research Virtual Machine,简称Jikes RVM)是一种成熟的用于执行Java程序的虚拟机,其早期版本与当前版本分别在通用公共许可证(CPL)与Eclipse公共许可证(EPL)下开...

匿名
2013/02/13
1K
0
Swing界面分析和调试工具--Swing Inspector

Swing Inspector是一个Java Swing/AWT用户界面分析和调试工具,功能与firebug类似,具有强大的Swing/AWT用户界面分析和调试相关功能。 适用于从java swing初级到高级的所有开发人员,能够快速...

匿名
2013/03/06
3.3K
0
Java™ 编译器--Janino

Janino是一个超级小但又超级快的Java™ 编译器. 它不仅能像javac工具那样讲一组源文件编译成字节码文件,还可以对一些Java表达式,代码块,类中的文本(class body)或者内存中源文件进行编译,...

匿名
2013/04/02
4.1K
0

没有更多内容

加载失败,请刷新页面

加载更多

Vim清除最后一个搜索突出显示 - Vim clear last search highlighting

问题: Want to improve this post? 想要改善这篇文章吗? Provide detailed answers to this question, including citations and an explanation of why your answer is correct. 提供此问题......

技术盛宴
55分钟前
23
0
原子属性和非原子属性有什么区别? - What's the difference between the atomic and nonatomic attributes?

问题: What do atomic and nonatomic mean in property declarations? 属性声明中atomic和nonatomic是什么意思? @property(nonatomic, retain) UITextField *userName;@property(atomic, ......

fyin1314
今天
7
0
马化腾每天刷 Leetcode?代码你打算写到几岁?

本文作者:o****0 前几天,一张未证真伪的截图流传,图中显示马化腾几乎每天都会在 Leetcode 上提交代码。 截图还贴出一个 Leetcode 账户地址。该地址的头像已从马化腾的照片换成腾讯 logo,...

百度开发者中心
前天
13
0
滴滴 3000+ Kylin Cube 背后的实践经验揭秘

本次分享主要有三个部分:Kylin 在滴滴的整体应用、架构的实践经验、滴滴全局字典最新版本的实现以及 Kylin 最新实时 OLAP 探索经验分享。 Kylin 在滴滴的应用&架构 Kylin 在滴滴的三类应用场...

浪尖聊大数据
昨天
9
0
ssh“权限太开放”错误 - ssh “permissions are too open” error

问题: I had a problem with my mac where I couldn't save any kind of file on the disk anymore. 我的Mac出现问题,无法再在磁盘上保存任何类型的文件。 I had to reboot OSX lion and r......

javail
今天
19
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部