java虚拟机内存可以分为独占区和共享区。

独占区:虚拟内存栈、本地方法栈、程序计数器。

共享区:方法区、Java堆(用来存放对象实例)。

  程序计数器

  比较小的内存空间,当前线程所执行的字节码的行号指示器,如果执行的为java方法,那么计数器记录的是正在执行的虚拟机字节码指令的地址,如果方法是native方法,则为undefined。

  字节码解释器工作时就是通过改变这个计数器的值来选取下一条需要执行的字节码指令,分支、循环、跳转、异常处理、线程恢复等功能都需要依赖这个计数器完成。

  在任何一个确定的时刻,一个处理器只能执行一条线程中的指令。因此,为了线程切换后能恢复到正确的执行位置,每条线程都需要有一个独立的程序计数器,各个线程之间的程序计数器互相不影响,独立存储。  

  Java虚拟机栈

  生命周期和线程相同。存放方法时运行的数据,描述的是Java方法执行的动态内存模型。

  栈帧:每次方法执行,就会创建一个栈帧,栈帧进栈就开始执行。如果调用其他方法,则又会创建一个栈帧,就按照栈的先进先出来进行。栈帧用来存储局部变量表、操作数栈、方法出口等。

  局部变量表:存放编译器可知的基本数据类型(boolean、byte、char、short、int、float、long、double)、对象引用等,大小不会改变。只有double和long会占用两个局部变量空间,其他只占用一个。局部变量表的大小在编译期间被确定。

  本地方法栈

  本地方法栈的作用和虚拟机栈作用相似,只不过虚拟机栈为Java方法(也就是字节码)服务,本地方法栈为Native方法服务。

  Java堆

  在大多数情况上来说,Java堆是Java虚拟机锁管理的内存中最大的一块。Java堆是被所有进程共享的一块内存区域。Java堆的目的就是存放对象实例,几乎所有的对象实例都要在这分配内存。

  Java堆在虚拟机启动时创建。

  Java堆是垃圾收集器管理的主要区域,所以又称GC堆。Java堆又可以分出来新生代和老年代,再细致一点可以分出来Eden、From Survivor、To Survivor空间。进一步的划分只要是为了更好地利用回收内存。

  Java堆可以处于物理上不连续的区域,只要它们逻辑上是连续的。

  方法区

  方法区用来存放已经被虚拟机加载的类信息、常量、静态变量等。

  在某些虚拟机上(HotSpot),方法区又称为永久代,这样垃圾收集器也可以管理方法区。

  运行时常量池

  运行时常量池是方法区的一部分。Class文件中除了有类的版本、字段、方法、接口等描述信息外,还有一项信息是常量池,用来存放编译期生成的各种字面量和符号引用,这部分在类加载后进入方法区的运行时常量池进行存放。

  运行期间也可以将新的常量存放在池中,如String类中的intern方法。

  Hotspot虚拟机在Java堆中全过程

  对象的创建

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

  在类加载检查通过后,接下来虚拟机将为新生对象分配内存。对象内存的大小在类加载完成之后便可以确定,为对象分配内存的任务等同于把一块确定大小的内存从Java堆中划分出来(指针碰撞和空闲列表,选择哪种方式由Java堆是否规整决定的)。

  内存分配完之后,虚拟机将分配的内存空间都初始化为零值(不包括对象头)。接下来,虚拟机将要对对象进行必要的设置,例如这个对象是哪个类的实例、如何才能找到类的元数据信息、对象的哈希码、对象的GC分代年龄等信息。这些信息存放在对象的对象头之中。

  在以上的工作完成之后,从虚拟机的角度上看,一个新的对象已经诞生了,但是从Java程序的角度看,对象创建才刚刚开始(init方法还没执行,所有字段都还为零),所以一般来说执行new指令之后再执行init方法,这样一个真正可用的对象才算产生出来。

  对象的内存布局

  在Hotspot虚拟机中,对象在内存的存储的布局分为3块:对象头、实例数据、对齐补充。

  对象头中包括两部分,第一部分用于存储对象自身的运行时数据,比如哈希码、GC分代年龄、锁状态标志、线程持有的锁、偏向线程ID,官方称之为Mark Word。考虑到虚拟机的空间效率,Mark Word被设计成一个非固定的数据结构以便在极小的空间中存储更多的信息。

  对象头的另外一部分是类型指针,就是对象指向它的类元数据的指针,从而虚拟机可以通过这个确定该对象是哪个类的实例。如果对象是一个数组,那么对象头中还有一段记录数组长度的数据。

  实例数据是对象真正存储的有效信息,也是代码中所定义的各种类型的字段内容。

  对其补充的作用就是JVM要求对象内存的起始地址必须是8字节的整数倍,所以用来补充保证满足这一个要求。

  对象的访问定位

Java虚拟机-内存tips的更多相关文章

  1. java虚拟机内存不足,“Could not create the Java Virtual Machine”问题解决方案

    java虚拟机内存不足,"Could not create the Java Virtual Machine"问题解决方案 在运行java程序时,遇到问题"Could n ...

  2. Java虚拟机内存模型及垃圾回收监控调优

    Java虚拟机内存模型及垃圾回收监控调优 如果你想理解Java垃圾回收如果工作,那么理解JVM的内存模型就显的非常重要.今天我们就来看看JVM内存的各不同部分及如果监控和实现垃圾回收调优. JVM内存 ...

  3. 如何设置Java虚拟机内存以适应大程序的装载

    Java虚拟机对于运行时的程序所占内存是有限制的,当我们的项目或者程序很大时,往往会照成内存溢出. 举个例子: public class SmallTest1 { public static void ...

  4. 打包apk java 虚拟机内存不足

    解决方案:在android->sdk->build-tools-android-version 中有个 dx.bat dx.bat --dex 命令的dx.bat脚本有这样一句代码 REM ...

  5. Java虚拟机内存溢出异常--《深入理解Java虚拟机》学习笔记及个人理解(三)

    Java虚拟机内存溢出异常--<深入理解Java虚拟机>学习笔记及个人理解(三) 书上P39 1. 堆内存溢出 不断地创建对象, 而且保证创建的这些对象不会被回收即可(让GC Root可达 ...

  6. JVM基础系列第6讲:Java 虚拟机内存结构

    看到这里,我相信大家对于一个 Java 源文件是如何变成字节码文件,以及字节码文件的含义已经非常清楚了.那么接下来就是让 Java 虚拟机运行字节码文件,从而得出我们最终想要的结果了.在这个过程中,J ...

  7. 总结Java虚拟机内存区域模型

    本篇文章主要来总结一下Java虚拟机内存的各个区域,以及这些区域的作用.服务对象以及其中可能产生的问题,作为大家的面试宝典. 首先我们来看一下Java运行时的数据区域,Java虚拟机在执行Java程序 ...

  8. Java虚拟机内存分配详解

    简介 了解Java虚拟机内存分布的好处 1.了解Java内存管理的细节,有助于程序员编写出性能更好的程序.比如,在新的线程创建时,JVM会为每个线程创建一个专属的栈 (stack),其栈是先进后出的数 ...

  9. 重读《深入理解Java虚拟机》一、Java虚拟机内存区域的划分

    一.Java虚拟机内存区域如何划分 1.Java虚拟机内存区域的划分 区域名称 作用(用途) 类型 特点 虚拟机规定异常情况 内存分配与回收 其他说明 1 程序计数器 指示当前正在执行的字节码指令地址 ...

随机推荐

  1. 汉字转拼音的Oracle函数

    前言: 最近处理一个特殊的问题,需要用到汉字自动转换拼音的功能. 解决: 在这里找了不少资料,都是有所缺陷,而且也好像很绕.其实是一个很简单的东东.后来还是自己写了一个函数获取.分享出来,给有需要的X ...

  2. Android项目-高考作文-AsyncTask的不足

    1, AsyncTask的不足. 从android4.0开始, 后台只允许一个AsyncTask执行, 如果当前的AsyncTask没有执行完毕, 那么当前的请求一直处于等待状态. 直到上一个执行完毕 ...

  3. MySQL 如何使用索引 较为详细的分析和例子

    在数据库表中,使用索引可以大大提高查询速度. 假如我们创建了一个 testIndex 表: CREATE TABLE testIndex(i_testID INT NOT NULL,vc_Name V ...

  4. UNIX环境高级编程——时间和日期

    由UNIX内核提供的基本时间服务是计算自国际标准时间公元1970年1月1日00:00:00以来经过的秒数.这种秒数是以数据类型time_t表示. 1.     time函数返回当前时间和日期: tim ...

  5. Touch Handling in Cocos2D 3.x(五)

    实现新英雄的放置功能 首先我们需要一个变量来保持我们当前移动英雄的引用,因此我们将添加一个私有实例变量.修改MainScene.m中的代码. 用: @implementation MainScene ...

  6. wing带你玩转自定义view系列(3)模仿微信下拉眼睛

    发现了爱神的自定义view系列,我只想说一个字:凸(艹皿艹 ) !!相见恨晚啊,早看到就不会走这么多弯路了 另外相比之下我这完全是小儿科..所以不说了,这篇是本系列完结篇....我要从零开始跟随爱哥脚 ...

  7. 《java入门第一季》之面向对象(抽象类其实不抽象)

    上一篇(http://blog.csdn.net/qq_32059827/article/details/51334198)对抽象类做了一些描述,这一篇根据两个案例加深一下印象.会觉得抽象类其实不抽象 ...

  8. 谈谈javascript 中的函数问题

    聊聊javascript中的函数 本文可作为李刚<疯狂htmlcssjavas讲义>的学习笔记 先说一个题外话 前几天在知乎上流传着一个对联  上联是雷锋推到雷峰塔 nnd 这是什么对联? ...

  9. OC语言(四)

    二十八.id类型(万能指针) 可以指向任何id对象(本身就是指针,不用*) id相当于NSObject *,类似于一种多态. 二十九.重写构造方法 new方法的实质:分配空间+alloc 和 初始化- ...

  10. 求剁手的分享,如何简单开发js图表

    前段时间做的一个项目里需要用到js图表,在网上找了下,大概找到了highcharts.fusioncharts这些国外产品. 因为都收费,虽然有盗版,我也不敢用,万一被找上们来就砸锅卖铁了要.自己写j ...