猿问

Java,在构造器里调用多态方法

class Glyph {

    void draw() { System.out.println("Glyph.draw()"); }

    Glyph() {

        System.out.println("Glyph() before draw()");

        draw();

        System.out.println("Glyph() after draw()");

    }

}

class RoundGlyph extends Glyph {

    private int radius = 1;

    RoundGlyph(int r) {

        radius = r;

        System.out.println("RoundGlyph.RoundGlyph(), radius = " + radius);

    }

    void draw() {

        System.out.println("RoundGlyph.draw(), radius = " + radius);

    }

    

    void superDraw(){

        super.draw();

    }


}

public class PolyConstructors {

    public static void main(String[] args) {

        RoundGlyph rg = new RoundGlyph(5);

        rg.superDraw();

    }

}

这样一段代码,执行结果是这样的:

Glyph() before draw()

RoundGlyph.draw(), radius = 0

Glyph() after draw()

RoundGlyph.RoundGlyph(), radius = 5

Glyph.draw()


Thinking In Java中有一句话


Glyph.draw()方法设计将要被覆盖,这种覆盖是在RoundGlyph中发生的。(这里都OK)但是Glyph构造器会调用这个方法,结果导致了对RoundGlyph.draw()的调用。


这句话我就不太明白了,①为什么Glyph的构造器会去调用子类的draw方法而不去调用自己的draw方法呢?重写明明是在子类中发生的呀,父类中的draw方法并没有被重写吧(看我后来又调了super.draw,结果也是父类中的draw方法)。

常见的多态代码是向上转型,把一个子类的实例赋值给父类的引用,这时候产生多态,这个我知道。但是②这个多态是怎么产生的呢?

主要就是①②这两个问题


茅侃侃
浏览 492回答 5
5回答

精慕HU

一般的函数覆盖的实现可以想象成类里面有一个指向函数的指针(或者引用函数的引用)。在派生类中,覆盖了相同签名的函数,就跟指针/引用所指向/引用的函数是另一个函数差不多。

紫衣仙女

为什么Glyph的构造器会去调用子类的draw方法而不去调用自己的draw方法呢?...RoundGlyph rg = new RoundGlyph(5); 这段代码在构造函数里传了一个整型参数多态的定义:指允许不同类的对象对同一消息做出响应。即同一消息可以根据发送对象的不同而采用多种不同的行为方式。(发送消息就是函数调用)。我认为你可以理解为不同类(父类、子类)里的构造函数会有不同的(构造)效果。

冉冉说

你可以理解成光调用方法其实本质上隐含了一个语义就是this.方法()你说的第二个问题没有看明白

波斯汪

你没理解java的方法解析.你可以在父类的构造器第一行添加下面这行代码System.out.println(this.getClass().getName());然后看看输出结果, 你应该就明白了。
随时随地看视频慕课网APP

相关分类

Java
我要回答