[jvm]运行时数据区域详解
了解虚拟机是怎么使用内存的,有助于我们解决和排查内存泄漏和溢出方面的问题。详解java虚拟机内存的各个区域,分析这些区域的作用服务对象以及可能发生的问题。
一、运行时数据区域
java虚拟机在执行java程序的过程中会把它所管理的内存区域划分为若干个不同的数据区域。这些数据区域都有各自的用途,以及创建时间和销毁时间。有的随着虚拟机进程的而存在,有些区域则依赖用户线程的启动和结束而建立和销毁。根据java虚拟机的规范,jvm管理的内存将包括以下几个运行时数据区域。
1.1 程序计数器
程序计数器是当前线程所执行程序字节码的行号计数器,字节码解释器根据这个程序计数器的值来选取下一条需要执行的字节码,实现程序的分支、循环、跳转、异常处理 和线程控制等基本功能。在java中,每个线程的执行需要操作系统轮换的分配处理机,因此每个线程都有自己的程序计数器,各个线程之间的计数器互不影响,独立存储,计数器占用空间不大。因此计数器是线程私有的内存。当线程正在执行java方法时,计数器的值为当前字节码指令的地址。当执行的是本地方法是,计数器的值为空。计数器是唯一一个不会发生OOM的数据区域。
1.2 java虚拟机栈
虚拟机栈和计数器一样,和线程私有的,它的生命周期和线程相同。虚拟机栈是java方法执行的内存描述:每一个方法的执行都会为其创建一个栈帧,用于存储局部变量表,操作数栈,动态链接和方法的出口信息,局部变量表存储了编译期可知的基本数据类型[byte,int,float,double,char,short,long,boolean],对象引用类型(不是实际的对象,可能只是对象的内存地址),进入一个方法后,局部变量表的内存空间在编译是完全确认的,方法运行期间不会改变其大小。每一个方法从调用到执行完成,都对应着一个栈帧在虚拟机栈中从入栈到出栈的过程。
该区域可能有两类异常:StackOverflowError:线程请求的深度大于虚拟机允许的深度;OutOfMemory:如果虚拟机栈可以动态扩展,但是扩展的时候无法申请到足够的内存。
1.3 本地方法栈
与java虚拟机栈类似,但是不同的是Java虚拟机栈是为java方法服务(字节码),本地方法栈是为非java语言但是虚拟机又使用到的方法服务的(比如类加载器中最顶层的实现使用的是c++)。同样的,本地方法栈也会抛出StackOverflowError和OutOfMemory异常。
1.4 java堆
java堆是被所有线程共享的一大片内存区域,其作用就是为创建的实例对象或者数组分配内存,也因此java堆是GC的主要针对区域,为了更好实现GC的效果,还把这一大块java堆内存分为不同的区域:叫什么Eden区,From区,Survivor,To Survivor;还有的从线程的角度甚至把这线程共享的java堆给各个线程分配了自己的缓冲区。真是树大招风啊!!但是无论java堆内存从什么角度被怎么划分,在这java堆中存放实例对象或者数组这一事实无法更改。进一步划分的目的是为了更加高效滴利用这一内存中的宝地罢了。根据规范,java堆的内存在物理上不要求连续,只要逻辑上连续就好了。
该区域可能抛出的异常:OutOfMemory:堆中没有内存足以给实例分配了
1.5 方法区
与java堆一样,也是线程共享的内存区域,主要用于存放已经被虚拟机加载的类信息,常量,静态变量,以及实时编译的数据。虽然我们很不愿意把方法区和java堆混为一谈,但是从GC的角度,GC就是将方法区看成是java堆的永久代。虽然GC在这“永久代”上的效果总不是那么理想,但是却必不可少,GC在永久代的目的是针对常量池的回收以及类型卸载。
该区域可能出现的异常:OutOfMemory:方法区无法满足内配时。
1.6 运行时常量池
线程共享的内存区域,运行时常量池属于方法区的一部分。java文件编译的Class文件中,除了类的基本信息(版本,字段,方法,接口等)之外,还有就是常量池,用于存放编译期间生成的字面量和符号引用(我觉得就是static,final修饰的字段吧),这部分内容在类被加载后就被放入运行时常量池了。除了Class文件中的符号引用外,还把翻译出来的直接引用也存储在运行时常量池了。运行时常量池还可以动态滴加入程序运行时生成的常量,比如String。
运行时常量池是方法区的一部分,那么自然也受到方法区内存的限制,当无法申请到内存时将抛出OutOfMemory。
二、直接内存
直接内存并不是java虚拟机运行时数据区域的一部分,也不是虚拟机规范中定义的内存区域,但是这部分内存常常也被频繁使用,而且也可能导致OutOfMemory,直接内存的分配虽然不受java堆大小的限制,但是既然是内存,那么必然受到本机物理内存的限制,我们在配置java虚拟机内存的时候,一定要注意java虚拟机各部分的内存总和不能大于本机实际的物理内存。
三、No Picture You Say a j8
转载于:https://www.cnblogs.com/ytuan996/p/10612468.html
[jvm]运行时数据区域详解相关推荐
- Java JVM内存模型(运行时数据区域)详解
详细介绍了JVM运行时数据区域,包括方法区.堆空间.栈空间.本地方法栈.程序计数器.常量池.直接内存.字面量.符号引用.直接引用. Java程序在运行时,需要在内存中的分配空间.为了提高运算效率,ja ...
- JVM——内存区域:运行时数据区域详解
关注微信公众号:CodingTechWork,一起学习进步. 引言 我们经常会被问到一个问题是Java和C++有何区别?我们除了能回答一个是面向对象.一个是面向过程编程以外,我们还会从底层内存管理 ...
- jvm中方法区和常量池详解_JVM——内存区域:运行时数据区域详解
关注微信公众号:CodingTechWork,一起学习进步. 引言 我们经常会被问到一个问题是Java和C++有何区别?我们除了能回答一个是面向对象.一个是面向过程编程以外,我们还会从底层内存管理和垃 ...
- JVM 运行时数据区详解,写得非常好!
作者:小小木的博客 www.cnblogs.com/wyc1994666/p/11795781.html 在接下来的几天想总结下,JVM相关的一些内容,比如下面的这三个内容算是比较核心知识点了 1.运 ...
- java 线程栈大小配置,JVM运行时数据区详解-Stack栈(优化配置、代码样例)
最近有段时间没有更新Netty的教程了,却发了一些其他的东西.可能有的朋友会问,难道这就完事了?不会的.两方面原因.第一.笔者也是需要工作的人,自然要完成好工作中的任务,这里面也有很多东西需要学习和研 ...
- 12.JDK1.8 JVM运行时数据区域概览、各区域介绍、程序计数器、Java虚拟机栈、本地方法栈、堆、堆空间内存分配(默认情况下)、字符串常量池、元数据区、jvm参数配置
12.JDK1.8 JVM运行时数据区域概览 12.1.JDK1.8 JVM运行时数据区域概览 12.2.各区域介绍 12.3.各区域介绍 12.3.1.程序计数器 12.3.2.Java虚拟机栈 1 ...
- JVM运行时数据区域——为什么jdk8用元空间替换了永久代
以局部窥全局,这个问题其实很复杂,要弄清楚这个问题,首先要对JVM运行时数据区域划分以及各个数据区域的作用了和指掌. JVM运行时数据区域总览 JVM在执行Java程序的过程中(简称运行时)会把它所管 ...
- JVM学习笔记② JVM运行时数据区域
JVM所管理的内存将会包括以下几个运行时数据区域: 方法区(Method Area) 方法区是各个线程共享的区域,存放类信息.常量.静态变量.即时编译器编译后的代码等数据.虽然Java虚拟机规范把方法 ...
- JVM调优系列:(二)JVM运行时数据区域
1) Method Area 2) Heap 3) Java Stacks 4) PC Registers 5) Native Method Stacks JAVA的JVM的内存模型大致可分为3个区: ...
最新文章
- 系统怎么手动打补丁_韩国服务器不稳定怎么办?
- VMware Workstation 6.0全貌概览
- Ansible详解(二)
- Nginx_日志文件讲解
- 习题7-2 求一批整数中出现最多的个位数字 (20分)
- P5020-货币系统【背包】
- 使用MAC 编译合约的时候报错:
- 一个词三个功能,较真人员少啊
- 【Unity3D插件】Dialogue System for Unity插件分享《对话系统插件》
- Git:每一行命令都算数
- root改手机型号王者,手机root后怎么改手机型号
- 爬虫问题小记 --- UnicodeEncodeError: 'gbk' codec can't encode character '\xa9' in position 25703: illegal
- 什么是JDBC,JDBC是干嘛用的?
- js获取随机数与随机颜色函数的简单封装
- 职业梦想是计算机的英语作文,梦想的职业英语作文
- Flink入门技术分享PPT之二
- Webservice与Servlet
- 煤矿井下定位系统黑科技—UWB
- 《数据分析方法论和业务实战》读书笔记
- Python开发环境的搭建(小白适用)