java对象创建(内存模型)过程详解

概述

java对象创建分为两个过程:声明对象引用和创建对象实体。类信息、对象引用、对象实体均在内存的不同区域。

内存结构

每一个java应用程序均会唯一的对应一个jvm实例,而这个jvm实例将会完成对象的内存分配、程序运行、垃圾回收等工作。JVM将其内存分为三个区域:方法区、栈区、堆区。

  • 方法区:是jvm在装载类文件时,用于存储类的所有描述信息的,这些信息主要包括,类的基本信息(访问修饰符、类名等)、字段信息(修饰符、类型、字段名)、方法信息(修饰符、返回值类型、方法名、参数列表类型、异常、方法体字节码等)、常量池、静态区、classloader以及class的引用
  • 栈区:存放局部变量,基本数据类型和对象引用类型
  • 堆区:用于存放new产生对象的实体,每一个对象实体均会有自己的内存地址,一旦这个内存地址不被任何栈区对象引用,就会成为垃圾,随时被gc回收

对象创建过程

package ccnu.allTest;

public class TestObject {
    public static void main(String[] args) {
        YyPpLl ypl1 = new YyPpLl();
        YyPpLl ypl2 = new YyPpLl(48);
        System.out.println((ypl1.ii == ypl2.ii) + " "+ YyPpLl.ii);
        System.out.println(ypl1.str == ypl2.str);
    }

    static class YyPpLl {
        private String str = "ypl"; // 显示初始化字段
        private int i; // 未显示初始化字段
        private static int ii = 24; // 静态字段
        private static int iii;
        static { // 静态初始化块
            System.out.println("ii=" + ii + ", iii=" + iii);
        }
        { // 实例初始化块
// iii = 100;
            System.out.println("str=" + str + ",i=" + i + ",ii=" + ii + ",iii=" + iii);
        }

        public YyPpLl(){
            ii = 72;
            System.out.println("non-arguments");
        }

        public YyPpLl(int i){
            this.i = i;
            System.out.println("two arguments");
        }

    }
}

/* ii=24, iii=0 str=ypl,i=0,ii=24,iii=0 non-arguments str=ypl,i=0,ii=72,iii=0 two arguments true 72 true */

  • 步骤:1、将JVM加载到内存
    2、jvm首先检查public类是否存在,存在就会将它加载到内存方法区中,否则抛出异常,结束进程
    3、对类中静态字段进行初始化(显示初始化就为指定的值,否则为默认值),接着执行静态代码块
    4、在栈中创建局部变量,堆中创建对象实体,为堆对象实体的成员变量(非静态)初始化,对于静态字段只需要从方法区的静态区中引用其值即可,执行构造代码块,接着执行构造函数(当然,调用顺序会一直上溯到Object类,每一个构造方法的第一行为super()语句),最后将对象实体堆地址给栈中引用变量

    要注意的是,实例字段包括自身定义的和从父类继承下来的(即使父类的实例字段被子类覆盖或者被private修饰,都照样为其分配内存)
    C++中的引用和JAVA的引用作对比,其实他们两个只是“名称”一样,本质并没什么关系,C++中的引用只是给现存变量起了一个别名(引用变量只是一个符号引用而已,编译器并不会给引用分配新的内存),而JAVA中的引用变量却是真真正正的变量,具有自己的内存空间,只是不同的引用变量可以“指向”同一个对象而已。因此,如果要拿C++和JAVA引用对象的方式相对比,C++中的指针倒和JAVA中的引用如出一辙,毕竟,JAVA中的引用其实就是对指针的封装

    原文作者:java内存模型
    原文地址: https://blog.csdn.net/Recall_Tomorrow/article/details/69815543
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞