在java开发中,jvm负责内存分配,对于开发者而已很省事,但是当你程序存在内存溢出或者内存泄漏时,你就很难定位到具体原因。
1. jvm的组成区域:方法区 ,堆,虚拟机栈,本地方法栈,程序计数器pc
方法区和堆是线程共享的,其余不是
2.程序计数器pc:是一块较小的内存空间,用于记录执行的位置。由于jvm的多线程是通 过线程交替和执行时间决定的,所以在交替的时候,必要pc判断执行的 位置。每个线程都需要独立存储的pc,pc也叫线程私有的内存。是唯一不 会有outOfmemeoryError 的区域。
3.堆:线程共享的区域,是jvm中最大的一块内存区域,基本的对象实例和数组都在堆上
分配,由于编译器和逃逸分析技术的发展,所以的对象实例都在堆上分配变的不那
绝对了。
堆是垃圾回收器管理的主要的区域,所以也叫gc堆。在gc堆中可分为新生代,老年
代。堆的物理区域可以不连续,逻辑上联系即可。随说是共享,但是可以有多划分
出多个线程私有的缓冲区。
会有outOfMemeoryErro
4.虚拟机栈: 线程私有,主要在程序执行过程中,分配局部变量存储区,变量存储区可
可叫局部变量表。局部变量存放编译期各种数据。
long & double 64位 占2个局部变量空间,其余的都1个。
如果程序请求的栈深度深于 jvm允许深度:StackOverFlowErro.
现在的jvm都可以动态扩展,若扩展还不够:outOfMemoryErro.。
5.本地方法栈:线程私有,本地方法栈跟虚拟机栈功能相似,本地方法栈主要是给native
方法执行分配空间,而虚拟机栈主要是给java语言的程序执行分配空间。
会有StackOverFlowErro 和outOfMeMeoryErro。
6.方法区:线程共享,主要是给类信息,常量,静态变量分配存储控制。有的虚拟机把方法区
直接划分为堆的逻辑部分,但其他的没有则叫非堆用于区分。方法区极小不回收,主
要是,对类信息回收的要求比较苛刻。主要的回收目标是常量和类型。有outOfMemeoryErro
注,运行时常量池 是方法区的一部分。