学习目的
了解代码在运行时的执行顺序
代码在运行时的执行顺序
上代码
package com.example.demo.basic;
/**
* 初始化执行顺序
*/
public class InitializationParents {
public static int count = 1;
static {
//快捷键sout-->System.out.println();
System.out.println("Parent 静态变量"+count);
System.out.println("Parent 静态块");
}
{
//快捷键sout-->System.out.println();
System.out.println("Parent 非静态块");
}
public InitializationParents(){
//初始化构造方法
System.out.println("Parent 构造方法");
}
}
第一种类型
package com.example.demo.basic;
/**
* 初始化执行顺序
*/
public class InitializationChild extends InitializationParents {
public static int count = 1;
static {
//快捷键sout-->System.out.println();
System.out.println("Child 静态变量"+count);
System.out.println("Child 静态块");
}
{
//快捷键sout-->System.out.println();
System.out.println("Child 非静态块");
}
public InitializationChild(){
//初始化构造方法
System.out.println("Child 构造方法");
}
public static void main(String[] args) {
System.out.println("-------start------");
InitializationChild child = new InitializationChild();
System.out.println("-------end------");
}
}
第一种类型执行结果
Parent 静态变量1
Parent 静态块
Child 静态变量1
Child 静态块
-------start------
Parent 非静态块
Parent 构造方法
Child 非静态块
Child 构造方法
-------end------
第二种类型
package com.example.demo.basic;
/**
* 初始化执行顺序
*/
public class InitializationChild extends InitializationParents {
public static int count = 1;
static {
//快捷键sout-->System.out.println();
System.out.println("Child 静态变量"+count);
System.out.println("Child 静态块");
}
{
//快捷键sout-->System.out.println();
System.out.println("Child 非静态块");
}
public InitializationChild(){
//初始化构造方法
System.out.println("Child 构造方法");
}
public static void main(String[] args) {
System.out.println("-------start------");
InitializationChild child = new InitializationChild();
InitializationChild child2 = new InitializationChild();
System.out.println("-------end------");
}
}
第二种类型执行结果
Parent 静态变量1
Parent 静态块
Child 静态变量1
Child 静态块
-------start------
Parent 非静态块
Parent 构造方法
Child 非静态块
Child 构造方法
Parent 非静态块
Parent 构造方法
Child 非静态块
Child 构造方法
-------end------
阿里面试题
package com.example.demo.basic;
/**
* 加载方法不等于执行方法,初始化变量则会赋值
* 类加载顺序应为 加载静态方法-初始化静态变量-执行静态代码块
* 实例化时 先加载非静态方法-实例化非静态变量-执行构造代码块-执行构造函数
*
*/
public class InitializationTest {
/**第一个加载*/
public static int k = 0;
/**第二个加载,因为是new一个实例,
* 首先初始化j 打印出 1:j i=0 n=0
* 执行构造块 打印出 2:构造快 i=1 n=1
* 执行构造方法 打印出 3:t1 i=2 n=2
* 实例化完成
*/
public static InitializationTest t1 = new InitializationTest("t1");
/**第三个加载 过程同上
* 首先初始化j 打印出 4:j i=3 n=3
* 执行构造块 打印出 5:构造快 i=4 n=4
* 执行构造方法 打印出 6:t2 i=5 n=5
*/
public static InitializationTest t2 = new InitializationTest("t2");
/**第四个加载
* 打印出 7:i i=6 n=6
*/
public static int i = print("i");
/**
* 第五个加载
*/
public static int n = 99;
/**
* 此变量在类加载的时候并不初始化,在实例化类的时候初始化
*/
public int j = print("j");
/**
* 第六个加载 此时,n已经被初始化 所以打印出
* 8:静态块 i=7 n=99
*/
static {
print("静态块");
}
//-----------以上属于类加载---------------------
/**
* 实例化过程:
* 首先加载非静态方法集;
* 初始化非静态变量:9:j i=8 n=100
* 执行构造块:10:构造快 i=9 n=101
* 执行构造方法:11:init i=10 n=102
* 实例化完成
*/
{
print("构造块");
}
/**
* 执行构造函数 实例化完成
* @param str
*/
public InitializationTest(String str) {
System.out.println((++k) + ":" + str + " i=" + i + " n=" + n);
++i;
++n;
}
/**
* 这个应该是最先加载 但是,加载不等于执行
* 因为如果不加载此函数,静态变量是无法初始化的
* @param str
* @return
*/
public static int print(String str) {
System.out.println((++k) + ":" + str + " i=" + i + " n=" + n);
++n;
return ++i;
}
public static void main(String args[]) {
/**首先加载类,然后实例化:
* 类加载过程:
* 首先加载所有的静态方法,但不执行;
* 然后按照静态变量的顺序开始初始化
* 静态变量初始化完毕后执行静态构造块(不执行构造块)
* 此时类加载完毕
* 实例化过程:
* 加载非静态方法
* 初始化非静态变量
* 执行构造代码块
* 执行构造函数
* 此时实例化完毕
*/
InitializationTest t = new InitializationTest("init");
}
}