Java 扩展子类的子类中的super()构造函数?

Java 扩展子类的子类中的super()构造函数?,java,inheritance,constructor,overriding,Java,Inheritance,Constructor,Overriding,我不确定我的问题措辞是否正确,但我对这些代码行感到困惑 public class First { public String name() { return "First"; } } public class Second extends First { public void whoRules() { System.out.print(super.name() + " rules"); System.out.printl

我不确定我的问题措辞是否正确,但我对这些代码行感到困惑

public class First {
    public String name() {
        return "First";
    }
}

public class Second extends First {
    public void whoRules() {
        System.out.print(super.name() + " rules");
        System.out.println(" but " + name() + " is even better");
    }
    public String name() {
        return "Second";
    }
}

public class Third extends Second {
    public String name() {
        return "Third";
    }
}

Second varSecond = new Second();
Third varThird = new Third();
varSecond.whoRules();
varThird.whoRules();
执行上述操作时,它会打印出来

First rules but second is even better

First rules but third is even better
为什么不是:

First rules but second is even better

Second rules but third is even better
子类可以是另一个类的超类吗?或者只能有一个(超类)? (使用上面的示例代码) 我知道
First
Second
的超类,但是
Second
Third
的超类吗? 还是
First
Third
的超类

如果有10个类彼此扩展(第二个扩展第一个,第三个扩展第二个,等等),那么所有这些类的超类都是
first
?)

为什么不是:。。。“第二条规则,但第三条更好”

因为类Second中的
super.name()
引用的是Second的超类,而不是实例的超类

来自:表单super.Identifier引用当前对象的名为Identifier的字段,但当前对象被视为当前类的超类的实例

子类可以是另一个类的超类吗

或者只能有一个(超类)

每个类最多可以有一个直接超类,而直接超类又可以有自己的超类,等等

(使用上面的示例代码)我知道第一个是第二个的超类,但第二个是第三个的超类吗?或者第一个是第三个的超类

第一个和第二个都是第三个的超类

第二个是第三个的直接超类

Third varThird = new Third();
因为第三个类没有whoRules()方法。它调用超类方法


如果在调用过程中没有指定对象,编译器将使用“this”关键字来调用。这就是为什么打印为“Third”的.name()作为whoRules()方法被第三类对象调用的原因。。因此,结果是“第一个规则,但第三个更好。”

这是因为您从第二个类调用super,而第二个类从第一个类调用super.name()。
第二个的超级总是第一个

这是简单的继承。第一类是第二类的超类,第二类是第三类的超类。基本上,当您创建第三类的对象时,它将继承第一类和第二类父类的所有(非私有)属性

First -> Second -> Third 
Super关键字-在给定的示例中,您首先在子类中重写(在子类中实现一个超类方法)超类的方法name(),然后在子类中重写。使用关键字Super.name()可以调用超类的name()方法

我想让你记住的最重要的事情是

java编译器根据引用类型调用方法,而不是 对象类型

当你说

varSecond.whoRules();
在这种情况下,对象引用属于第二类

System.out.print(super.name() + " rules");//calls the name() in class First
System.out.println("but" + name()+"is even better");//calls the name() in class Second
但是当你说

varThird.whoRules();
在这种情况下,对象引用属于第三类

System.out.print(super.name() + " rules");//calls the name() in class First
System.out.println("but" + name()+"is even better");//calls the name() in class Third
因为name()方法是在第三个类中定义的。如果您没有在第三个类中定义name()方法,它会调用超级类方法


回答你的另一个问题,继承的深度没有硬性限制,但通常情况下,在一个好的设计中,你不会在层次结构中看到10个超类

何时/如何引用Second?关键字“super”仅在Second的直接子类中引用Second类。如果需要对象类的超类,可以通过从这个.getClass()返回的类对象来实现。这完全是错误的:“java编译器调用基于引用类型而不是对象类型的方法”@你能解释一下这是怎么回事吗?动态方法调用是基于运行时的对象类型,而不是编译时的引用类型。这是面向对象开发的基石之一。@Andythonas Cramer我对java bit不是很有经验,我首先提到过,他们至少说过5次同样的话。那本书说编译器使用引用类型,看看你是否可以调用该方法。在运行时调用的实际方法基于对象类型。请参阅。
super.name()
存在于第二个类中,尽管继承了方法
whoRules()
,但其中的
super.name()
仍然指向第二个
的超类的名称,在您的例子中,它是
第一个