超类引用不应该能够调用它的子类独有的方法

时间:2015-03-01 22:47:05

标签: java inheritance

但是,如果超类有一个抽象方法,并且该方法在它的子类中实现,这是具体的,我们仍然可以使用超类的Object调用子类的方法实现。

怎么回事?

对于重载方法,即使使用超类的引用调用它,也会调用子类的实现。

让我在这里更具体......

假设Animal是一个超类,Dog是一个子类。 现在,我做:

Animal a = new Dog();

这意味着a是对动物类的引用,对吧?

现在,如果我这样做,a.function(); (假设该函数在Animal中定义并在Dog中被覆盖),Animal的版本应该被称为是对动物的引用,但它是另一种方式。

1 个答案:

答案 0 :(得分:1)

这意味着超类不能调用子类中定义的方法,因为超类不知道它们。对于抽象方法,超类知道它们,因此它可以调用它们。非抽象和非最终方法也会发生这种情况:子类可以修改它们而不会注意到超类,超级类仍然可以正常工作。

您所描述的是编译时间和执行时间(也称为运行时间)之间的差异。在编译时,变量只能调用在声明变量的类型上定义的方法,例如Animal animal然后animal变量只能调用Animal类中定义的方法。在执行时,该方法的执行将由属于对象引用的实例的类处理,例如, Animal animal = new Dog();然后animal行为将由Dog类中所述的行为定义。

示例:

public class Animal {
    abstract void breath();
}

public class Dog extends Animal {
    @Override
    public void breath() {
        System.out.println("Dog breathing");
    }

    public void bark() {
        System.out.println("woof!");
    }
}

public class Client {
    public static void main(String[] args) {
        //animal variable is of type Animal
        //and initialized as a Dog object reference
        Animal animal = new Dog();

        //dog variable is of type Dog (also an Animal)
        //and initialized as a Dog object reference
        Dog dog = new Dog();

        animal.breath();
        dog.breath();

        //line below throws a compiler exception
        //since animal is declared as type Animal
        //not all Animals know how to bark
        animal.bark();

        //line below compiles fine
        //since dog is declared as type Dog
        //and Dog's know how to bark
        dog.bark();
    }
}