代码:
父类:
class Father {
private String name;
//无参构造
Father() {
System.out.println("--父类的无参构造函数--");
}
//有参构造
Father(String name) {
this.name = name;
System.out.println("--父类的有参构造函数--" + this.name);
}
//静态代码块
static {
System.out.println("--父类的静态代码块--");
}
//非静态代码块
{
System.out.println("--父类的非静态代码块--");
}
//父类speak()方法
public void speak() {
System.out.println("--父类的方法--");
}
}
子类:
public class Son extends Father {
private String name;
//静态代码块
static {
System.out.println("--子类的静态代码块--");
}
//非静态代码块
{
System.out.println("--子类的非静态代码块--");
}
//子类无参构造函数
Son() {
System.out.println("--子类的无参构造函数--");
}
//子类有参构造函数
Son(String name) {
super(name);
this.name = name;
System.out.println("--子类的有参构造函数--" + this.name);
}
//子类覆盖父类方法
public void speak() {
System.out.println("--子类覆盖了父类的方法--");
}
//子类主程序
public static void main(String[] args) {
System.out.println("--子类主程序--");
Son s1= new Son("儿子的名字");
Son s2= new Son();
s1.speak();
}
}
注意:在子类构造方法引用父类构造方法时,应放在子类构造方法中的第一行。
运行结果:(再查看运行结果之前不妨先自己思考一遍答案)
--父类的静态代码块--
--子类的静态代码块--
--子类主程序--
--父类的非静态代码块--
--父类的有参构造函数--儿子的名字
--子类的非静态代码块--
--子类的有参构造函数--儿子的名字
--父类的非静态代码块--
--父类的无参构造函数--
--子类的非静态代码块--
--子类的无参构造函数--
--子类覆盖了父类的方法--
结论:
子类继承父类时,各代码段的执行顺序:
优先级:
1.父类静态代码块>子类静态代码块
2.静态代码块>主程序(静态代码块只执行一次)
3.非静态代码块>构造函数(如果主函数有构造函数,执行非静态代码块后再执行构造函数)
4.父类构造函数>子类构造函数(非静态代码块执行多次,与引用构造函数次数有关)
5.最后执行普通方法(注意普通方法里面是否有执行父类方法、是否覆盖父类方法,覆盖了则执行子类方法)