Java运行时内存数据区域分布

    xiaoxiao2025-11-13  1

    基本类型定义的变量应该存储在堆中,因为这些变量肯定在类内,类肯定在堆中。类肯定是new出来的。看java开发实战经典93页(5.2.3对象的创建与使用),可以看出,new出来的类,类里的基本类型的属性,在堆中,因为它属于对象的具体内容。

    ==========================

    转载自:http://blog.csdn.net/Stars_Moon_Sky/article/details/43805803

     JVM在执行Java程序的过程中会把它所管理的内存划分为若干个不同的数据区域,这些区域都有着各自的用途,创建和销毁的时间。

        

        JVM运行时的数据区被划分为:程序计数器,虚拟机栈,本地方法栈,Java堆,方法区。

        程序计数器:线程私有,即每个线程都会分配一块内存空间,用做程序计数,对汇编有所了解的应该知道,汇编中有一个专门的程序计数器PC,二者是一样的,用来指示下一条需要执行的字节码。

                       如果线程正在执行的是一个Java 方法,那么计数器中记录的是下一条将要执行的字节码的地址;若是正在执行的是Native方法,这个值就为空。

                       这个区域是唯一一个在Java虚拟机规范中没有规定任何OutOfMemoryError情况的区域(程序可以无限大)。

       

         虚拟机栈:线程私有,每个线程都会有一块栈空间区域,线程运行时调用的方法会被视作一个的栈帧,执行一个方法就是将栈帧入栈,方法返回就是将栈帧出栈。栈帧中包括局部变量表,操作数,动态连接,方法的出口等。我们通常说java内存分为栈和堆,这是很粗略的分法,其中的栈一般指局部变量表。

                    关于基本数据类型分配空间问题:除了long和double占据两个局部变量空间以外,其余的都只占据一个局部变量空间,以后会说道到,称之为slot。

                    局部变量表所需的内存空间在编译期间就会确定下来,在方法运行时不会改变局部变量表的大小。

                    异常:当栈空间的大小不能扩展时,如果申请的空间超过了虚拟机栈所允许的最大的深度,会出现StackOverflowError异常;如果栈可以动态扩展,扩展都  无法申请到足够的内存,会出现OutOfMemoryErrorError 异常。 

       

         本地方法栈:类似虚拟机栈,不同之处在于:虚拟机栈执行的是Java方法,本地方法栈执行的是本地方法。

                            本地方法指用非Java语言实现的Java方法,关键字native

        Java堆:线程共享,这块区域的唯一目的就是存放对象实例,几乎所有的对象实例都存放在这里(并不是所有,逃逸分析技术,标量替换

                          技术可能会导致一些微妙的变化发生,直接将对象分配到栈上)。每个线程的TLAB也是在这个地方进行分配。

                         堆内存空间关键区域只要在逻辑上连续的即可,物理上可以不连续。

                        当堆无法扩展时,会出现OutOfMemoryError异常。

       方法区:线程共享,存放常量,静态变量等,它是堆的一个逻辑部分,但它有一个别名叫Non-Heap.

                       方法区的运行时常量池并不要求常量只能在编译期产生,在运行时也可加入新的常量。

                       class文件的常量池包含编译期产生的各种字面量与符号引用,类加载就存放到方法区的运行时常量池。

                      无法满足内存分配需求时,会出现OutOfMemoryError异常。

      直接内存:这并不是JVM运行时数据区的一部分。

                            JDK1.4中新加入类NIO类,引入了一种基于通道和缓冲区的I/O方式,可以直接分配堆外内存。

    转载请注明原文地址: https://ju.6miu.com/read-1304162.html
    最新回复(0)