在下面代码中有3个类 主类Test 另外2个就是子类和副类的关系了
在下面代码中画有(/////////////不懂)的记号 请大家帮我看看
class Supers

int i =1;
Supers(){System.out.println("Supers()");}
void a(){ System.out.println("a()in Supers()");}
void b(){ System.out.println("b()in Supers()");}
void speak(Supers p ){System.out.println("I am Supers");}
}class Sub extends Supers
{
int i=2;
Sub()
{
System.out.println("Sub()");
}
void a()
{
System.out.println("a()in Sub()");
}
void speak(Sub s )
{
System.out.println("I am sub");
}
}public class Test
{
public static void main(String args[])
{
Supers b=new Sub();
Sub c=new Sub();
System.out.println(b.i);  /////////不懂
b.a();
b.b(); //////////没有重写b方法所以执行复类的b方法
b.speak(c); //////////////////不懂
c.speak(c);
}
}

解决方案 »

  1.   

    System.out.println(b.i);  //由b的声明类型(Supers)决定
    b.speak(c); //调用Supers的speak,由于Sub的speak并不是override Supers的speak
      

  2.   

    第一个问题还是不懂啊!不知道原因啊!第2个问题:Sub中没有覆盖父类的sperk方法。因为参数的类型 Sub类中speak方法参数是Sub,而Supers类中的方法参数是Supeak。
    所以没有覆盖.但是c是Sub类型,而父类的speak方法中参数类型是Speak啊,他为什么会不调用c的speak方法呢?
      

  3.   

    //第一个问题还是不懂啊!不知道原因啊!
    说得很明确了,由编译时类型确定。如b.i就是1,c.i就是2//但是c是Sub类型,而父类的speak方法中参数类型是Speak啊,他为什么会不调用c的speak方法呢?你比较以下2个就知道了,由this确定
    b.speak(c);  // 编译时确定调用Supers.speak(Supers), 运行时b真实类型是Sub,但Sub类并没有override此方法,所以调用父类speak
    c.speak(c);  // 编译时确定调用Sub.speak(Sub)你可以把Sub的speak的参数类型改为Supers试试
      

  4.   

    b.speak(c);  // 编译时确定调用Supers.speak(Supers), 运行时b真实类型是Sub,但Sub类并没有override此方法,所以调用父类speak
    答:
    是不是因为编译时确定了 调用父类的方法,子类中只是重载并没有覆盖,所以还是调用父类的speak方法(这是在编译时确定的),就算父类中speak方法中的参数不同,由于Spuers类型是Sub类型的父类,所以传递过去的c被向上转成拉supers对象,这对调用父类中speak方法是没有影响的