Java 对象在内存之中长什么样子的

202 阅读3分钟

jvm内存结构

想要了解Java对象在内存之中存储,首先要先了解jvm的的内存结构。这里大概介绍一下jvm的内存模型

image.png

--摘自彻底理解JVM内存模型 - 知乎 (zhihu.com)

这是一张非常经典的jvm内存结构图。

线程栈:程序运行时每调用的一个方法就会在栈中开辟一块内存空间,称为栈帧,栈帧内包含局部变量表,操作数栈(一些取值赋值操作的地方),动态链接,方法出口等。局部变量就保存在局部变量表之中,当然局部变量表也是一个栈结构。

堆:堆是jvm结构中最大的一块,主要用来保存Java对象。

方法区:类被类加载器会生成各类信息,类的方法代码,变量名,方法名,访问权限,返回值,静态变量,运行时常量池等等。

详解

package com.suancaiyu.student;

public class Student {
    public String name;
    public int age;
    public int score;

    public String getName() {
        return name;
    }

    public Student(String name, int age, int score) {
        this.name = name;
        this.age = age;
        this.score = score;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public int getScore() {
        return score;
    }

    public void setScore(int score) {
        this.score = score;
    }
}
package com.suancaiyu.student;

public class text {
    public static void main(String[] args) {
        Student tom=new Student("张三",20,80);
        System.out.println(tom.age);
    }
}

这里我们准备了一个Student类,并且在text类main方法里面new了一个Student对象如何引用它的一个属性值。

变量名

在理解栈内存的之前我们先要知道一个概念,变量是什么,变量名是地址的映射,比如 int a=10;

10这个数据存储在栈内存之中,假设他的地址是Ox73800004,那么a就是这个地址的映射,存在一个映射函数将这个地址值映射成为a。

例子详解

启动main方法,main方法被压入线程栈,生成栈帧,声明一个Student类型的变量,变量tom被压入局部变量表之中(也是栈结构),执行new方法会在堆内存声明一块内存空间用于保存student对象。

当执行Student tom=new Student()时,jvm会在内存之中生成这样的一个结构。

image.png

栈内存中保存的是Java对象在堆内存的起始地址,Java对象由mark word,class指针以及自身字段组成,mark word和class指针是由jvm自动给我们生成,mark word占4个字节里面存储一些锁信息,class指向方法区内的Class 对象,这也是为什么实例对象上都有一个.getclass()方法。

和我们理解不一样的是可能是堆内存的结构,在里面并没有存储字段名字,那么jvm是如何准确的引用对象的每一个字段的呢?

以tom.age为例,在执行这段语句时,首先会根据变量名tom找到在栈内存之中,再根据栈内存存储的地址值去找到堆内存中储存的对象,引用age之前会跟随class指针来到方法区找到age的引用规则,offset就是age的引用规则,意思是从起始地址往后移动12位就是age的存放地址,接下来只要往下读4个字节就可以读出age的值来了,需要注意的是name字段在堆内存里存放的还是一个地址值,因为他是一个引用数据类型,也是一个Java对象。

文章灵感来自---【Java必备知识】Java中的对象长什么样?_哔哩哔哩_bilibili

我按照这位老师所讲的添加了一点自己的理解。