JVM学习笔记二

对象的创建

首先,检查new指令的参数是否能在常量池中定位到一个类的符号引用,并且检查该符号引用所代表的类是否已经被加载、解析、初始化过。如果没有,需要 执行相应的类加载过程。

其次,虚拟机为新生对象分配内存。对象所需的内存大小在类加载完毕后便可以确定。

然后,虚拟机需要将分配的内存空间都初始化为零值(不包含对象头),保证了对象实例字段在Java代码中可以不赋值就直接使用。

接下来,虚拟机对对象进行必要的设置,比如:该对象是哪个类的实例、如何找到类的元数据信息、对象的哈希码、对象的GC分代年龄等信息。存在在对象头中。

虚拟机视角,该对象已经创建完毕。

一般来说,执行new指令之后,会紧接着执行<init>方法,把对象按照写作者的意愿进行初始化,这样一个对象才完全产生出来。

另附:

一、如何分配内存

  1. “指针碰撞”(Bump the Pointer):假设Java堆中是绝对规整的(用过的内存在一边 空闲的内存在一边 中间放一个指针作为分界点的指示器),分配内存就是把指针向空闲空间方向移动一块与对象大小相等的距离。

  2. “空闲列表”(Free List):如果Java堆中不是规整的,已使用的和空闲的相互交错,虚拟机就必须维护一个列表,来记录哪些内存块是可用的,在分配的时候在列表中找一块足够大的空间划分给对象实例,并且更新表上的记录。

二、并发情况下如何在堆上为对象分配内存

  1. 对内存分配空间的动作进行同步处理(虚拟机采用CAS配失败重试的方式来保证更新的原子性)

  2. 把内存分配的动作按照线程划分在不同的空间之中进行。也就是每个线程在Java堆中预先分配一小块内存,称为本地线程分配缓冲(Thread Local Allocation Buffer,TLAB)。哪个线程需要分配内存,就在哪个线程的TLAB上分配,只有

  在TLAB用完并分配新的TLAB时,才需要同步锁定。虚拟机是否使用TLAB,可通过参数 -XX:+/-UseTLAB 参数来设定。

猜你喜欢

转载自www.cnblogs.com/kawin/p/9986546.html
今日推荐