面向对象编程(基础)3:对象的内存解析

目录

3.1 JVM内存结构划分

 3.2 对象内存解析

举例:

内存解析图:

面试题:对象名中存储的是什么呢?

3.3 练习


3.1 JVM内存结构划分

HotSpot Java虚拟机的架构图如下。其中我们主要关心的是运行时数据区部分(Runtime Data Area)。

其中:

堆(Heap)此内存区域的唯一目的就是存放对象实例,几乎所有的对象实例都在这里分配内存。这一点在Java虚拟机规范中的描述是:所有的对象实例以及数组都要在堆上分配。

栈(Stack):是指虚拟机栈。虚拟机栈用于存储局部变量等。局部变量表存放了编译期可知长度的各种基本数据类型(boolean、byte、char、short、int、float、long、double)、对象引用(reference类型,它不等同于对象本身,是对象在堆内存的首地址)。 方法执行完,自动释放。

方法区(Method Area):用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。

 3.2 对象内存解析

举例:

class Person { //类:人
    String name;
    int age;
    boolean isMale;
}

public class PersonTest { //测试类
    public static void main(String[] args) {
        Person p1 = new Person();
        p1.name = "赵同学";
        p1.age = 20;
        p1.isMale = true;

        Person p2 = new Person();
        p2.age = 10;

        Person p3 = p1;
        p3.name = "郭同学";
    }
}

内存解析图:

说明:

堆:凡是new出来的结构(对象、数组)都放在堆空间中。
对象的属性存放在堆空间中。
创建一个类的多个对象(比如p1、p2),则每个对象都拥有当前类的一套"副本"(即属性)。当通过一个对象修改其属性时,不会影响其它对象此属性的值。
当声明一个新的变量使用现有的对象进行赋值时(比如p3 = p1),此时并没有在堆空间中创建新的对象。而是两个变量共同指向了堆空间中同一个对象。当通过一个对象修改属性时,会影响另外一个对象对此属性的调用。

面试题:对象名中存储的是什么呢?

答:对象地址

public class StudentTest{
    public static void main(String[] args){
        System.out.println(new Student());//Student@7852e922

        Student stu = new Student();
        System.out.println(stu);//Student@4e25154f
        
        int[] arr = new int[5];
		System.out.println(arr);//[I@70dea4e
    }
}

直接打印对象名和数组名都是显示“类型@对象的hashCode值",所以说类、数组都是引用数据类型,引用数据类型的变量中存储的是对象的地址,或者说指向堆中对象的首地址。

3.3 练习

根据代码,画出内存图

class Car {
    String color = "red";
    int num = 4;

    void show() {
        System.out.println("color=" + color + ",num=" + num);
    }
}

class CarTest {
    public static void main(String[] args) {
        Car c1 = new Car();   //建立对象c1
        Car c2 = new Car();   //建立对象c2
        c1.color = "blue";   //对对象的属性进行修改
        c1.show();   //使用对象的方法
        c2.show();
    }
}

猜你喜欢

转载自blog.csdn.net/swx595182208/article/details/129950822