class Meal
{
Meal() {System.out.println("Meal()");}
} class Bread
{
Bread() {System.out.println("Bread()");}
}class Cheese
{
Cheese() {System.out.println("Cheese()");}
}class Lettuce
{
Lettuce() {System.out.println("Lettuce()");}
}class Lunch extends Meal
{
Lunch() {System.out.println("Lunch()");}
}class PortableLunch extends Lunch
{
PortableLunch() {System.out.println("PortableLunch()");}
}public class Sandwich extends PortableLunch
{
private Meal m = new Meal();
private Bread b = new Bread();
private Cheese c = new Cheese();
private Lettuce l = new Lettuce();
public Sandwich(){
System.out.println("Sandwich()");
} public static void main(String[] args) 
{
new Sandwich();
}
}

解决方案 »

  1.   

    程序执行的结果是:
    Meal()
    Lunch()
    PortableLunch()
    Meal()
    Bread()
    Cheese()
    Lettuce()
    Sandwich()能解释一下程序执行的过程吗?
      

  2.   

    new Sandwich(); //这里要构造Sandwich对象
    按照继承关系
    构造Sandwich前先构造PortableLunch,
    构造PortableLunch先构造Lunch,
    构造Lunch前先构造Meal
    所以
    Meal->Lunch->PortableLunch
    然后构造Sandwich的时候,先走定义部分
    private   Meal   m   =   new   Meal(); 
    private   Bread   b   =   new   Bread(); 
    private   Cheese   c   =   new   Cheese(); 
    private   Lettuce   l   =   new   Lettuce(); 
    再走构造函数
    所以,就是你的结果了。
      

  3.   

    一般一个对象创建时:
    1、执行静态块中的代码,但它只执行一次
    2、如果被创建对象的类有父类,则在执行这个类的构造方法之前要先调用一个父类的构造器。如果父类又是继承自另一个类,则在父类的构造器被执行之前又要先调用父类的父类的构造器......
    3、完成之后调用类本身的构造器
    对于第二点,可以做一个实验:
    class FatherClass{
        public FatherClass(int arg){
        }
    }class ChildClass extends FatherClass{
        ChildClass(){
            super(1); // 省略这一句将编译通不过
        }
        public static void main(String[] args){
            new ChildClass();
        }
    }