精华内容
下载资源
问答
  • 在这里对象就是new 出来的Car ,这个对象被存放在堆内存里面,而c是这个对象的引用一般java程序运行时会涉及到如下几个存储区域:程序计数器:可以看做是当前所执行字节码的行号指示器。通常是改变计数器字节码的值...

    .java中的堆栈:

    如  Car c = new Car();

    在这里对象就是new 出来的Car ,这个对象被存放在堆内存里面,而c是这个对象的引用

    一般java程序运行时会涉及到如下几个存储区域:

    程序计数器:

    可以看做是当前所执行字节码的行号指示器。通常是改变计数器字节码的值来抉择下一步索要执行的代码,程序员不直接控制。

    寄存器:

    在程序中我们无法直接控制,由编译器管理。

    栈区:

    1,每个线程包含一个栈区,栈中只保存基础数据类型的对象和自定义的对象的引用以及局部变量。

    2,每个栈中的数据都是私有的,其他栈不能访问。

    3,当局部数据用完时,所占内存空间会自动释放。

    JVM栈一个最大的用处是为执行

    java方法服务的,每一个方法被执行的时候都会同时创建一个栈帧用于存储局部变量表,操作栈,动态链接,方法出口等信息。

    每一个方法从调用直至执行完成的过程都对应着一个栈帧在虚拟机中从入栈到出栈的过程。

    栈的优势在于存取速度比较快,仅次于寄存器。缺点是存储在栈中的数据的大小和生存周期是确定的,缺乏灵活性。

    堆区:

    1,通过new建立的数组和对象都存储在堆中。

    2,每一个对象都有相应的内存地址值。

    3,对象中的变量都有默认初始化值。

    4,数组和对象在没有引用变量指向它的时候,才变成垃圾,不能再被使用,但是仍然占着内存,在随后的一个不确定的时间被垃圾回收器释放掉。

    另外要明确的是每一个Java应用都唯一对应一个JVM实例,每一个实例唯一对应一个堆。在java堆中还必须包含能查找到对象类型数据(如对象类型,父类,实现的接口,方法等)的地址信息,

    这些类型数据(优先于对象存在)都存储在方法区中。

    堆的优势在于可以动态地分配内存的大小,生存周期也不必事先告诉编译器,因为它是运行时动态地分配内存的,并用垃圾回收机制回收那些不用的数据。缺点是存取速度比较慢。

    fba2fc55c0dacfa421c79139229f611a.png

    堆内存里面创建的对象一开始所有的成员变量都被初始化为null,即(new Car();)

    然后将new Car()的对象地址赋值给c,这个时候c就指向了堆内存中的对象,c就是对象的引用

    然后通过c的引用改变堆内存的对象的成员变量的值,如:c.color ="red"; c.num = 6;

    还有一种情况就是  ar c2 = c1;

    这种情况就是将c的内存地址赋值给c2,这时候c1 和c2 就同时指向一个对象,即如下:

    ed5a97c04688de7e0decc4832c7a9c44.png

    一般是通过对象的引用来访问对象。待补充和修改

    展开全文
  • Java对象的内存结构Java对象的内存结构包括:对象头实例数据对齐填充普通对象和数组对象,在内存结构上有一些不同,主要体现在对象头中。普通对象的对象头由Mark Word和Klass Pointer组成,而数组对象,对象头还包括...

    Java对象占用内存大小--Java对象的内存结构分析

    前言

    本文主要介绍Java对象的内存结构。

    Java对象的内存结构

    Java对象的内存结构包括:

    对象头

    实例数据

    对齐填充

    普通对象和数组对象,在内存结构上有一些不同,主要体现在对象头中。普通对象的对象头由Mark Word和Klass Pointer组成,而数组对象,对象头还包括一个数组长度。

    具体结构如下图:

    2ae497975fac6b4982310fb32132befc.png

    对象头

    普通对象:

    Mark Word:包含HashCode、分代年龄、锁标志等。

    Klass Pointer:指向当前对象的Class对象的内存地址。

    数组对象:

    Mark Word:包含HashCode、分代年龄、锁标志等。

    Klass Pointer:指向当前对象的Class对象的内存地址。

    Length:数组长度

    实例数据

    存储对象的所有成员变量,static成员变量不包括在内。

    对齐填充

    Java对象的内存空间是8字节对齐的,因此总大小不是8的倍数时,会进行补齐。

    Java对象的内存占用大小分析

    工具:JOL

    为便于分析对象的内存结构,可以使用JOL(Java Object Layout)工具来查看,地址:https://openjdk.java.net/projects/code-tools/jol/

    插件:JOL Java Object Layout

    也可以使用IDEA插件,进行可视化分析

    具体分析

    64位VM,开启压缩

    首先,看下Object的内存结构。

    引入JOL的jar包,通过下面代码就可以看到内存结构:

    Object object = new Object();

    System.out.println(ClassLayout.parseInstance(object).toPrintable());

    输出结果:

    d6b0138f3738ebba4d4edeb4da7a0daa.png

    可以看到,对象头中的Mark Word占8个字节,Klass Pointer占4个字节,然后补齐了4个字节,总大小为16个字节。

    以上结果是VM的默认配置时的输出。由于测试时的机器为64位HotSpot VM,JDK为1.8,因此是默认开启了指针压缩。

    64位VM,关闭压缩

    下面通过修改VM参数,来关闭指针压缩:

    -XX:-UseCompressedOops

    再次执行测试代码,输出结果:

    176544a3ba9db5c920a98a8f60775918.png

    和默认开启指针压缩不同的是,Klass Pointer占用8个字节,由于Mark Word+Klass Pointer=16,因此不需要再补齐。

    由于本机是64位的VM,因此在不压缩的情况下,Klass Pointer是占用8个字节。而Mark Word不管是否压缩,都占用8个字节。

    fa175bc55eaac5bfceaf73e9125aed44.png

    32位VM

    32位VM,不能开启压缩。

    32位的VM对象头对应的内存占用大小如下图:

    6948d9b93f5af97a027e34b99f181e18.png

    可以借助JOL Java Object Layout的插件进行查看。

    在对象类型上右键,选择Show Object Layout

    be938bc88b7a0e78dd3d830776ac032b.png

    在弹出的界面中选择32位VM,可以看到Object是占用8个字节,即4个字节的Mark Word+4个字节的Klass Pointer。

    f78ecdfb7f5ba96451f7fe7a99a86de6.png

    引用类型数组的内存结构

    执行以下代码

    Object[] objects = {new Object(), new Object()};

    System.out.println(ClassLayout.parseInstance(objects).toPrintable());

    输出结果

    49ed51a2c0c77b6848537ff42b68307a.png

    上图是64位VM,开启压缩的内存结构情况。这里只关注数组长度,可以看到长度占4个字节。实际数据占8个字节,即2*4个字节。

    关闭压缩后的结果:

    01883cec26204427113e4d9d067d5739.png

    可以看到长度占4个字节。实际数据占16个字节,即2*8个字节。

    基本类型数组的内存结构

    执行以下代码

    int[] nums = {1,2};

    System.out.println(ClassLayout.parseInstance(nums).toPrintable());

    输出结果

    3d64872f285d9c0fe6d309b3cbd3bf8b.png

    上图是64位VM,开启压缩的内存结构情况。这里只关注数组长度,可以看到长度占4个字节。实际数据占8个字节,即2*4个字节。

    关闭压缩后的结果:

    8c4a5a8b1e44390fbc331e765c947724.png

    可以看到长度占4个字节,由于:(8个字节的Mark Word+8个字节的Klass Pointer+4个字节的Length+8个字节的数据长度)不是8的倍数,因此进行了4个字节的补齐。实际数据占8个字节,即2*4个字节。

    小结

    32位的VM

    Mark Word占用4个字节,Klass Pointer占用4个字节,数组长度占用4个字节。实际数据:引用类型占用4个字节。

    64位的VM

    开启压缩

    Mark Word占用8个字节,Klass Pointer占用4个字节,数组长度占用4个字节。实际数据:引用类型占用4个字节。

    关闭压缩

    Mark Word占用8个字节,Klass Pointer占用8个字节,数组长度占用4个字节。实际数据:引用类型占用8个字节。

    对象头中锁标识

    执行以下代码,分析加锁前后对象头的数据变化

    Object object = new Object();

    System.out.println(ClassLayout.parseInstance(object).toPrintable());

    synchronized (object) {

    System.out.println(ClassLayout.parseInstance(object).toPrintable());

    }

    执行结果

    a989a9d002e37d07be33531108821dbf.png

    可以看到,在执行synchronized代码里,Object的对象头数据发生了变化,这是因为锁标识是存放在对象头中的,在执行synchronized代码时,会对锁进行标识。

    JOL常用方法

    JOL常用的三个方法

    ClassLayout.parseInstance(object).toPrintable():查看对象内部信息

    GraphLayout.parseInstance(object).toPrintable():查看对象外部信息,包括引用的对象

    GraphLayout.parseInstance(object).totalSize():查看对象总大小

    List list = new ArrayList<>();

    for (int i = 0; i < 15; i++) {

    list.add(i);

    }

    //查看对象内部信息

    String innerInfo = ClassLayout.parseInstance(list).toPrintable();

    System.out.println("对象内部信息");

    System.out.println(innerInfo);

    //查看对象外部信息,包括引用的对象

    String outInfo = GraphLayout.parseInstance(list).toPrintable();

    System.out.println("对象外部信息");

    System.out.println(outInfo);

    //查看对象总大小

    long totalSize = GraphLayout.parseInstance(list).totalSize();

    System.out.println("对象总大小");

    System.out.println(totalSize);

    执行结果

    9db78a0d66873aa6a007b609f5773224.png

    展开全文
  • Java对象结构

    2020-11-29 14:57:41
    储存到对象数据类型的指针 32/64bit Array length 数组的长度 Mark Word结构 锁状态 25bit 4bit 1bit(是否是偏向锁) 2bit(锁标志位) 无锁状态 对象的hashcode 对象分代年龄 0 01 在运行期间,若...

    java对象头

    java对象头长度

    长度 内容 说明
    32/64bit Mark Word 储存对象的hashcode等信息
    32/64bit Class Metadata Address 储存到对象数据类型的指针
    32/64bit Array length 数组的长度

    Mark Word结构

    锁状态 25bit 4bit 1bit(是否是偏向锁) 2bit(锁标志位)
    无锁状态 对象的hashcode 对象分代年龄 0 01

    在运行期间,若对象有锁,则会有以下结构变化

    锁状态 25bit 4bit 1bit 2bit
    23bit 2bit 是否是偏向锁 锁标志位
    轻量级锁 指向栈中记录锁的指针 00
    重量级锁 指向互斥量(重量级锁)的指针 10
    GC标志 11
    偏向锁 线程id Epoch与对象分代年龄共用(3bit+3bit) 1 01
    64位虚拟机下,Mark Word结构如下
    锁状态 25bit 31bit 1bit 4bit 1bit 2bit
    cms_free 分代年龄 偏向锁 锁标志位
    无锁 unused hashcode 0 01
    偏向锁 ThreaID(54bit) Epoch(21bit) 1 01
    展开全文
  • Java对象结构

    2021-03-19 10:57:10
    1. Java对象结构: 1.1 Java对象实例: 对象头: markword klass 对象实际数据: InstanceData 对齐填充: -padding 1.2 Java数组实例: 对象头: markword klass length 对象实际数据: ArrayData ...

    1. Java对象结构:

    1.1 Java对象实例:

    • 对象头
      • markword
      • klass
    • 对象实际数据
      • InstanceData
    • 对齐填充
      • padding

    1.2 Java数组实例:

    • 对象头
      • markword
      • klass
      • length
    • 对象实际数据
      • ArrayData
    • 对齐填充
      • padding

    解释:

    • markword:用于存储对象自身的运行时数据,如哈希码(hashcode)、GC分代年龄、锁状态标志、线程持有的锁、偏向线程ID、偏向时间戳等。32位、64位虚拟机中长度分别为32bit和64bit。

    • klass:klass类型指针,即对象指向它的类元数据的指针,虚拟机通过这个指针来确定这个对象是哪个类的实例。

    • length:数组长度(只有数组对象才有),用于记录数组的长度

    • InstanceData:是对象真正存储的有效信息,记录子类、父类的所有字段内容;

    • padding:占位符作用,用于对齐填充。

    2. OOP-Klass模型:

    klass:类被接在到内存时,被封装成了klass,记录类的全部信息,如类的方法、常量池等;
    oop:普通对象指针,包含markword和元数据指针;

    2.1 设计原理:

    klass里面会有虚函数表,同一个类的不同实例的klass都是同一个,oop-klass模型可以避免每个实例数据都拥有虚函数表。

    2.2 注意:

    实例中成员变量的分布并不是按照class的编码顺序排列的,为了提高性能,会重新进行排序,可以通过UNSAFE.objectFieldOffset来获取字段的偏移量。

    3. 对象的访问定位:

    3.1 句柄访问:

    在这里插入图片描述
    优势:当进行垃圾回收后,如果对象被移动,只需要改变句柄池中对象实例指针地址,Reference不用修改。

    3.2 直接指针访问:

    在这里插入图片描述
    优势:访问对象的速度更快,因为少了句柄访问对象这个中间过程。

    Hotspot使用的是直接指针访问

    展开全文
  • java对象结构

    千次阅读 2018-07-07 10:32:14
    java对象结构是由Header对象头、InstanceData、Padding组成   目录 Header(对象头) InstanceData Padding   Header(对象头)  1、自身运行时的数据(Mark Word)    ...
  • JVM内存结构、Java内存模型和Java对象模型是截然不同的三种概念。1. JVM内存结构Java程序执行过程中,内存会被划分为不同的数据区域,各个区域有各自的用途。有些区域随虚拟机的启动而存在有些区域随线程的启动而...
  • Matlab 2008b 才开始引入 containers.Map ,这是 Matlab 唯一的数据结构(这里的数据结构是指自带一定逻辑性的数据结构,不包括普通数据类型)。如果要有其它,比如 Queue、Set 等数据结构,只能自己编写一个。File ...
  • Java数据结构

    2012-11-24 19:30:12
    Java数据结构,清晰版 数据结构和算法有什么作用、数据结构的好处、算法的概述、面向对象编程
  • Java对象转换,代码比较简单 提供了两个查询方法: No.1 :Map<String,List<Tree>>arrMap= queryGroupToMap();//No.1(不推荐使用,运行时间较长) No.1.1:Map<String,List<Tree>>arrMap=.....
  • java 普通对象结构 java 数组对象结构 对象结构组成 对象头 HotSpot虚拟机的对象头包括两部分信息: Mark Word 第一部分Mark Word,用于存储对象自身的运行时数据,如哈希码(HashCode)、GC分代年龄、锁状态标志...
  • java对象结构

    万次阅读 多人点赞 2017-04-19 22:31:57
    先转载一篇文章作为开头,因为讲的非常详细,我就简单加工下放到这里: ...下图是普通对象实例与数组对象实例的数据结构对象头 HotSpot虚拟机的对象头包括两部分信息: markword 第一部分markwo...
  • Redis作为key-value内存数据库,支持丰富的数据类型,本文将以Java对象形式展示Redis内存模型。 Redis常用数据类型有string、hash、list、set和zset(其余几种不做讨论) DictEntry public class DictEntry { private...
  • Java对象占用内存大小–Java对象的内存结构分析 前言 本文主要介绍Java对象的内存结构Java对象的内存结构 Java对象的内存结构包括: 对象头 实例数据 对齐填充 普通对象和数组对象,在内存结构上有一些...
  • JAVA对象结构

    2017-05-25 16:51:50
    而对象再通过类型数据数据指针,找到类型数据(就是Class),然后与实例数据(运行时的对象数据)结合成对象。不管 new 多少个 Class AA, AA对像的类型数据只会在方法区中存一份,而对象实例数据而会对一对一的增加。...
  • List,Set 都是针对一组相同类型的对象数据结构,以下成为 组数据结构 ,Map 则是另一种 字典数据结构 。本人才疏学浅,如有错误,望各位批评指正,共同进步,感谢。 接口类型 在 Java 8 数据结构这块的源码中,...
  • Java对象结构杂谈

    2020-04-05 17:08:03
    Java虚拟机类型众多,本文以主流jvm之一HotSpot为例来说说Java对象结构,在内存中用三块区域用于存储对象,分别是对象头(Header)、实例数据(Instance Data)和对齐填充(Padding)。图为普通对象实例结构,数组...
  • Java数据结构与面向对象编程基础
  • Java语言中,对象是数据类型的实例,数据类型包含数据结构 对象 = 数据类型的实例 数据类型 = 数据结构+数据操作; 数据结构 = 数据元素+数据关系; 现实中 小明是人类对象的一个实例。 人类都有人体结构 ...
  • java对象和数组是存放在堆中的,那么这些instance的数据结构是什么呢? 对象头:对象头存放的是这个对象的一些元数据信息。例如每个对象都有哈希值,GC分代年龄,锁状态标志等,这些信息就是存放在对象头中。 ...
  • Java中的数据结构Java是一门面向对象编程语言,不仅吸收了C++语言的各种优点,还摒弃了C++里难以理解的多继承、指针等概念,因此Java语言具有功能强大和简单易用两个特征。那么Java中的数据结构是怎样的呢?以下仅供...
  • Java数据结构与算法2(面向对象栈结构-出栈、入栈) package Stack; import java.util.Arrays; public class MyStack { //使用数组来实现栈结构 int[] elements; public MyStack(){ elements = new int[0];...
  • java基础数据结构

    2018-04-07 12:27:21
     今天趁空闲时间总结下java中的相关的数据结构的知识点。1.Array数组Java中除了8中基本类型,数组也是作为对象处理的,所以创建对象时也需要使用new关键字。和大多数编程语言一样,数组一旦创建,大小便不可改变。...
  • Matlab 2008b才开始引入containers.Map,这是Matlab唯一的数据结构(这里的数据结构是指自带一定逻辑性的数据结构,不包括普通数据类型)。如果要有其它,比如Queue、Set等数据结构,只能自己编写一个。File Exchange...
  • 数据结构的概述算法的概述一些定义面向对象编程软件工程对于C++程序员的JavaJava数据结构的类库小结问题第2章 数组Array专题AppletJava中数组的基础知识将程序划分成类类接口Ordered专题applet有序数组的Java代码...
  • Java.util包中含有诸如向量(一个可扩充的数组)、栈、哈希表等类型的数据结构,使用包需要import java.util.*。所有不包括在表1.2中的类型,如String、数组,都是类,或者叫对象类型,创建一个对象时使用关键字new,...
  • Java数据结构与算法3(面向对象队列结构-出队、入队) package Queue; import java.util.Arrays; //队列思想:先进先出 public class MyQueue { //使用数组实现队列结构 int[] elements; public MyQueue(){ ...
  • Java对象结构

    2019-07-17 17:03:56
    Java对象结构如下所示: 在HotSpot虚拟机中,对象在内存中存储的布局可以分为3块区域:对象头(Header)、实例数据(Instance Data)和对齐填充(Padding)。 HotSpot虚拟机的对象头包括两部分信息: 对象自身...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 19,435
精华内容 7,774
关键字:

java对象数据结构

java 订阅
数据结构 订阅