java内存区域分析及java对象的创建

java虚拟机在执行java程序的过程中会将它管理的内存区域加分为若干个的不同的数据区域.

主要包括以下几个运行时数据区域,这里就只介绍经常会用到的

1:java虚拟机栈:我们常说的堆栈,栈就是指的java虚拟机栈

  作用:java方法执行的内存模型。每个方法在执行的时候会创建一个栈帧,这个栈帧保存了局部变量表(基本类型,对象引用),操作数栈,动态链接等

            一个方法的开始与结束的过程,就是栈帧进出java虚拟机栈的过程

2:java堆:存放对象实例,是内存最大的一块,垃圾收集器主要管理放入区域

3:方法区:存储了加载的类信息(如类名,访问修饰符,字段描述,方法描述),常量(常量存储在运行时常量池里,但运行时常量池是方法区的一部分,这里常量池也包括存储通过String,intern()本地动态生成的常量)

4:了解了java虚拟机的内存区域划分以后,在讲讲对象是如何创建的

当java虚拟机运行程序时,碰到new指令(假设这个引用代表的类已经被加载、解析、初始化,就像用橡皮泥模板化捏大象,首先你要有大熊的模板),将会为这个对象分配内存,内存大小在类加载完成以后即可确定(有了大象的模板以后,你就大概知道需要多少橡皮泥了),为java分配内存的方法有两种:1):如果内存规整的话,可以采用指针碰撞  2)反之,空闲列表,感觉这里用橡皮泥的列子好像不合适,如果一种颜色的橡皮泥一直分配去做大象就是指针碰撞,如果随意找颜色,如果那块橡皮泥不够用来做大象,就换一种,直到找到符合能做大象颜色的橡皮泥就是空闲列表。分配完内存以后,就对内存进行初始化0,接着对对象进行初始化(主要是对对象头的设置),但是现在的初始化只是针对java虚拟机来说是完成了的,对java程序来说还未完成,最后一步,按照程序员的意思对对象进行初始化,我的理解是按照程序员的意思调用构造器对字段进行初始化,所以我到这里也明白了jaba编程思想里说的所有的字段会在方法(包括构造器之前先初始化为默认的初值)

5:java对象在堆内存又可以分为三块区域,1是对象头,(保存哈希码,gc年龄代,锁状态标识买现成持有锁,偏向线程ID等等,还有类型指针,确定是哪个对象的实列,但并不是每个对象都有) 2是实列数据, 3是对象填充,因为对象必须是8字节的整数倍,对象头是8字节的整数倍,所以当对象实列数据部分没有对其时,就需要通过对齐来填充

6:对象的访问定位:两种方式:1)使用句柄 2)使用直接指针、

这张图直接明确:

第二种方式比第一种方式节省了一次指针定位的开销,所以速度更快

                                                                                             

                                                                   总结知识点辛苦,转载请说明出处。如有讲解不当的地方,请多多指教

原文地址:https://www.cnblogs.com/Hdaydayup/p/7494072.html