Java对象初始化顺序为:类加载时执行父类静态块→子类静态块(各一次),new时执行父类构造块→父类构造方法→子类构造块→子类构造方法;静态块触发需主动使用类,构造块与变量按源码顺序执行。

排查Java对象初始化顺序,关键在于理解执行时机和观察实际输出。静态代码块只在类加载时执行一次,构造代码块每次new对象时都执行、且在构造方法之前。只要按步骤加日志,就能清晰看到执行链条。
看类加载触发点
静态代码块的执行取决于“类首次被主动使用”。常见触发方式包括:调用静态方法、访问静态字段(非final常量)、new该类实例、反射加载Class.forName()。注意:单纯声明引用或import不会触发加载。
- 如果静态代码块没执行,先确认是否真的触发了类加载——比如main里只写了Parent p;但没new,就不会走静态块
- 用System.out.println("类名已加载");放在静态块里,配合启动时打印,可验证是否加载成功
- 多个类存在继承关系时,父类静态块一定先于子类静态块执行,且各自只执行一次
用日志标记每个阶段
在每种代码块和构造方法里打带标识的日志,是最直接的排查手段。重点区分“类级”和“实例级”动作:
当用户要求为 Java 代码添加注释、修改注释、审查注释、整理注释格式,或要求按照代码注释规范处理 Java 文件时,使用本技能。本技能用于统一生成和维护 Java 类注释模板、按 Git 对比 release 判断版本号、补充每行代码上方中文块注释、调整注释空行规则,并保持 Java 文件 UTF-8 无 BOM 编码。典型触发场景包括:补充类注释、更新 @version、检查 @author 来源、整理行尾注释、把注释放到代码上一行、检查注释是否符合规范、构建前检查 Java 注释风格。
- 静态代码块中写System.out.println("【静态】父类加载");
- 构造代码块中写System.out.println("【实例】父类构造块");
- 构造方法中写System.out.println("【实例】父类构造方法");
- 避免只写“开始”“结束”,要带上来源类名和阶段类型,否则多层继承时容易混淆
注意代码块定义顺序的影响
同一个类中,多个静态代码块按书写顺序执行;多个构造代码块也按出现顺序执行,且都在构造方法调用前运行:
- 例如类里先写{ System.out.println("A"); },再写{ System.out.println("B"); },new对象时必然先输出A再输出B
- 静态变量赋值语句(如static int x = 10;)和静态代码块混合时,变量声明初始化优先于静态块中代码执行,但整体仍属于类加载阶段
- 普通成员变量初始化(如int y = 20;)和构造代码块交替出现时,它们的执行顺序与源码中定义顺序一致
借助调试器单步验证
在IDE中对静态代码块第一行、构造代码块第一行、构造方法首行分别打断点,然后debug运行:
- 第一次new时,会依次停在父类静态块→子类静态块→父类构造块→父类构造方法→子类构造块→子类构造方法
- 第二次new时,静态块断点不会再命中,但构造块和构造方法断点会再次触发
- 观察调用栈(Call Stack),能清楚看到当前是类加载流程还是对象实例化流程
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










