一、对象的创建过程

对象的创建过程大致可以分为六步,其中对象的分配尤为重要:

二、对象分配内存

一般来说对象分配内存有两种方式:

第一种是指针碰撞,这是一种比较理想的方式:如果Java堆是绝对规整的:一边是用过的内存,一边是空闲的内存,中间一个指针作为边界指示器;分配内存只需向空闲那边移动指针,这种分配方式称为"指针碰撞"(Bump the Pointer);

第二中方式是空闲列表,这中方式没有指针碰撞那么理想,但是也有他自身的优势:如果Java堆不是规整的:用过的和空闲的内存相互交错; 需要维护一个列表,记录哪些内存可用;分配内存时查表找到一个足够大的内存,并更新列表,这种分配方式称为"空闲列表"(Free List);

这两种方式各有各的优势,具体选用方式,需要根据垃圾收集器来进行选择,主要是根据垃圾回收器有无压缩来选择。

三、线程安全问题

在进行并发操作时,上面两种方式分配内存的操作都不是线程安全的,所以考虑到解决这种线程安全问题:

第一种:加锁,这种方式是开发过程中最容易使用的方式,也是最简单的方式,但是这种方式的缺点就是执行效率太低。

第二种:本地线程分配缓冲区(TLAB):把分配内存的动作按照线程划分在不同的空间中进行:在每个线程在Java堆预先分配一小块内存,称为本地线程分配缓冲区(Thread Local Allocation Buffer,TLAB);哪个线程需要分配内存就从哪个线程的TLAB上分配。

四、对象的结构

对象的结构分为三部分:

第一部分:Header(对象头),对象头又有两给部块组成

1.自身运行时数据(Mark word),这部分数据是对象主要存储的数据,主要有:

a.哈希值:这个值是通过一个native方法获取

b.GC分代年龄:这个是垃圾回收算法使用

以上介绍两种作用是太相同的,至于剩下的:c.锁状态标志、d.线程持有的锁、e.偏向线程ID、f.偏向时间戳都是作用于线程优化的

2.类型指针:对象指向类对象本身数据的指针

第二部分:实例数据(InstanceData):

实例数据部分是对象真正存储的有效信息,也既是我们在程序代码里面所定义的各种类型的字段内容,无论是从父类继承下来的,还是在子类中定义的都需要记录下来。 这部分的存储顺序会受到虚拟机分配策略参数(FieldsAllocationStyle)和字段在Java源码中定义顺序的影响。HotSpot虚拟机 默认的分配策略为longs/doubles、ints、shorts/chars、bytes/booleans、oops(Ordinary Object Pointers),从分配策略中可以看出,相同宽度的字段总是被分配到一起。在满足这个前提条件的情况下,在父类中定义的变量会出现在子类之前。如果 CompactFields参数值为true(默认为true),那子类之中较窄的变量也可能会插入到父类变量的空隙之中。

第三部分:对齐填充(Padding)

第三部分对齐填充并不是必然存在的,也没有特别的含义,它仅仅起着占位符的作用。由于HotSpot VM的自动内存管理系统要求对象起始地址必须是8字节的整数倍,换句话说就是对象的大小必须是8字节的整数倍。对象头正好是8字节的倍数(1倍或者2倍),因此当对象实例数据部分没有对齐的话,就需要通过对齐填充来补全。

五、对象的访问定位

对立对象是为了使用对象.Java程序需要通过在栈上的reference数据操作堆上的具体对象. 由于reference类型在Java虚拟机规范中只规定了一个指向对象的引用,并没有定义这个引用应该通过何种方式去定位,访问堆中的对象的具体位置,所以对象的访问方式取决于虚拟机的实现而定的.。简单来说 栈指向堆中只会指向地址,至于地址存储的是否对象,我们是无法知道的,

    解决这一问题目前有两种方式:

第一种:句柄指针:栈指向堆中的句柄池,句柄池中有实例对象的地址,通过句柄池指向对象

优点:栈地址永远不会改变,或者说引用地址不会改变

第二张:直接指针:reference中存储直接对象的地址,但是必须考虑放置访问类型数据的相关信息

优点:效率快,节省了一次指针定位的时间开销

深入了解java虚拟机(JVM) 第四章 对象的创建的更多相关文章

  1. [core java学习笔记][第四章对象与类]

    4.3 用户自定义类 4.3.1 类数组的声明 需要两次new Employee[]=staff=new Employedd[3]; staff[0]=new Employedd(参数列表); sta ...

  2. 《深入理解Java虚拟机》(四)虚拟机性能监控与故障处理工具

    虚拟机性能监控与故障处理工具 详解 4.1 概述 本文参考的是周志明的 <深入理解Java虚拟机> 第四章 ,为了整理思路,简单记录一下,方便后期查阅. JDK本身提供了很多方便的JVM性 ...

  3. [三] java虚拟机 JVM字节码 指令集 bytecode 操作码 指令分类用法 助记符

    说明,本文的目的在于从宏观逻辑上介绍清楚绝大多数的字节码指令的含义以及分类 只要认真阅读本文必然能够对字节码指令集有所了解 如果需要了解清楚每一个指令的具体详尽用法,请参阅虚拟机规范 指令简介 计算机 ...

  4. Java虚拟机笔记(四):垃圾收集器

    前言 前一篇文章介绍了内存的垃圾收集算法,现在介绍下内存回收的具体实现--垃圾收集器. 由于Java虚拟机规范中对垃圾收集器应该如何实现并没有任何规定,因此不同的厂商,不同版本的虚拟机所提供的垃圾收集 ...

  5. 深入理解JAVA虚拟机JVM

    深入理解JAVA虚拟机JVM Java 虚拟机(Java virtual machine,JVM)是运行 Java 程序必不可少的机制.java之所以能实现一次编写到处执行,也就是因为jVM.原理:编 ...

  6. 《Java程序设计》第四章-认识对象

    20145221<Java程序设计>第四章-认识对象 总结 教材学习内容总结 类与对象 定义:对象是Java语言中重要的组成部分,之前学过的C语言是面向过程的,而Java主要是面向对象的. ...

  7. 深入理解java虚拟机JVM(下)

    深入理解java虚拟机JVM(下) 链接:https://pan.baidu.com/s/1c6pZjLeMQqc9t-OXvUM66w 提取码:uwak 复制这段内容后打开百度网盘手机App,操作更 ...

  8. Java虚拟机JVM学习07 类的卸载机制

    Java虚拟机JVM学习07 类的卸载机制 类的生命周期 当Sample类被加载.连接和初始化后,它的生命周期就开始了. 当代表Sample类的Class对象不再被引用,即不可触及时,Class对象就 ...

  9. Java虚拟机JVM学习06 自定义类加载器 父委托机制和命名空间的再讨论

    Java虚拟机JVM学习06 自定义类加载器 父委托机制和命名空间的再讨论 创建用户自定义的类加载器 要创建用户自定义的类加载器,只需要扩展java.lang.ClassLoader类,然后覆盖它的f ...

随机推荐

  1. win10 wsl安装 命令行

    用于一些精简版没有商店的安装方法 开启"Windows Subsystem for Linux" 可选特性 打开`PowerShell`,运行下面指令: Enable-Window ...

  2. shell编程——流控制case和select

    在shell编程里有时候需要出现交换界面,让使用者来选择要执行的功能,如下面所示,这时候就需要用到case和select进行配合 请选择功能: 1) 退出 2) 系统升级 3) 防火墙配置 4) to ...

  3. Build/Run Instructions for Codec Engine Examples

    General Information This page explains how to build the examples provided in the Codec Engine (CE) p ...

  4. Excel VBA入门(五)Excel对象操作

    本章是本系列教程的重点.但我觉得应该不是难点.从第零章开始到学完本章,应该可以把VBA用于实战中了. Excel对象主要有4个: 工作薄 Workbook 工作表 Worksheet 单元格区域 Ra ...

  5. Android开发实战之底部Dialog弹出效果

    在Android开发中,有很多情况下我们需要使用到对话框,遗憾的是,安卓自带的对话框样式不能满足我们实际的需要,所以往往需要我们自定义对话框,具体做法:写一个对话框继承自Dialog实现他的一个构造方 ...

  6. 124. Binary Tree Maximum Path Sum (Tree; DFS)

    Given a binary tree, find the maximum path sum. For this problem, a path is defined as any sequence ...

  7. 平衡二叉树之AVL树

    AVL树(命名来源于作者姓名,Adelson-Velskii和Landis),即平衡二叉树,满足以下的条件: 1)它的左子树和右子树都是AVL树 2)左子树和右子树的高度差不能超过1 从条件1可能看出 ...

  8. 面向对象JS基础

    什么是面向对象?面向对象是一种思想!(废话). 面向对象可以把程序中的关键模块都视为对象,而模块拥有属性及方法.这样我们如果把一些属性及方法封装起来,日后使用将非常方便,也可以避免繁琐重复的工作.接下 ...

  9. [C++] CONST 2

    The C++ 'const' Declaration: Why & How The 'const' system is one of the really messy features of ...

  10. ubuntu 16.04 nfs服务的搭建

    nfs服务是实现Linux和Linux之间的文件共享,nfs服务的搭建比较简单. 现在介绍如何在ubuntu16.04系统中搭建nfs服务,ubuntu的搭建比红帽的还要简单. 1.安装nfs服务 s ...