Java中静态块,初始化块及构造函数的执行顺序

我们可以将执行顺序大致看作:
         1. 静态成员    //静态的域或方法只在加载类时执行一次
         2.初始化块
         3. 构造函数

其实初始化块和构造函数可以看成一个整体,(执行构造函数之前先执行这个类的初始化块)。当然在执行子类之前先执行父类相应的方法。(另外需要注意的一点是在执行子类的构造方法之前会先执行父类的默认构造函数即无参构造函数)

在我们学习之前,我们先来看一段代码:

public class Employee {
	⑴private String name = "lisi";
	⑵{
		System.out.println("初始化1");
		name = "wangwu";
		age = 20;
	}
	⑶private int age = 30;
	⑷static {
		System.out.println("静态初始化1");
		System.out.println("id0:" + Employee.id);
		id = 40;
		System.out.println("id1:" + Employee.id);
		System.out.println("liuliu开始");
		Employee employee = new Employee("liuliu", 50);
		System.out.println(employee);
		System.out.println("liuliu id:" + employee.getId());
		System.out.println("liuliu结束");

	}
	⑸private static int id = 30;

	⑹{
		System.out.println("初始化2");
		name = "zhaosi";
		age = 40;
	}
	⑺static {
		System.out.println("id2:" + Employee.id);
		System.out.println("静态初始化2");
		id = 80;
		System.out.println("id3:" + Employee.id);

	}

	public static int getId() {
		return id;
	}

	public String getName() {
		return name;
	}

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

	public Employee(String name, int age) {
		super();
		System.out.println("有參構造器");
		this.name = name;
		this.age = age;
	}

	public Employee() {
		super();
		System.out.println("無參構造器");
		// TODO Auto-generated constructor stub
	}

	@Override
	public String toString() {
		return "Employee [name=" + name + ", age=" + age + "]";
	}

}
public static void main(String[] args) {
		System.out.println("tom开始");
		Employee tom = new Employee("tom", 20);
		System.out.println(tom);
		System.out.println(tom.getId());
		System.out.println("tom结束");
		System.out.println("jouty开始");
		Employee jouty = new Employee("jouty", 19);
		System.out.println(jouty);
		System.out.println(jouty.getId());
		System.out.println("jouty结束");
	}

你觉得最后输出结果会是什么呢?不妨自己先试一试!
最后输出为

    然后我们来分析一下:

1.输出**“tom开始”**
2.初始化tom对象,输出**“静态初始化1”
    定义tom对象,调用类employee,首先执行第一个static块,输出了
“静态初始化1”"id0:0"(虽然之后定义了id的静态变量为30,但是在加载类的时候,只是将变量的声明提前了,并未对它赋值,所以输出的是id的默认值0);
    然后赋值id=40,输出
“id1:40”;然后输出“liuliu开始”,然后初始化employee对象,按顺序执行了(1),(2)输出“初始化1”,(3),(6)输出“初始化2”,然后执行构造函数,输出“有参构造器”
    然后回到之前static块中,输出employee对象(即执行其tostring方法),输出
“Employee【name=liuliu,age=50】”;然后输出“liuliu id:40”;最后“liuliu结束”
3.然后执行(5)
4.然后执行(7):
    输出(5)所执行的赋值,即输出
“id2:30”
    然后输出
“静态初始化2”
    执行id=80;输出
“id3:80”;至此,就已经执行完了类中的所有静态的域和方法了;
5.然后执行类中的非静态变量和方法,块:
    按顺序执行(1),(2)输出
“初始化1”,(3),(6)输出“初始化2”,然后执行构造函数,输出“有参构造器”
    返回主函数main()中,输出tom对象(即执行其tostring方法),输出
“Employee【name=tom,age=20】”
6.输出id的值
“80”;输出“tom结束”“jouty开始”
7.开始初始化jouty对象:
    按顺序执行(1),(2)输出
“初始化1”,(3),(6)输出“初始化2”,然后执行构造函数,输出“有参构造器”
    返回主函数main()中,输出jouty对象(即执行其tostring方法),输出
“Employee【name=jouty,age=19】”
8…输出id的值
“80”;输出“jouty结束”**

    总而言之,在Java中,静态域和静态方法都是在类加载是执行的,所以是第一个执行,然后在实例化对象时,执行非静态变量和方法(按书写顺序执行),一般构造函数的主体都写在初始化块之后
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值