我有两个班级,
abstract class Shape {
protected DrawAPI drawAPI;
protected Shape(DrawAPI drawAPI){
this.drawAPI = drawAPI;
}
public abstract void draw();
}
class Circle extends Shape {
private int x, y, radius;
public Circle(int x, int y, int radius, DrawAPI drawAPI) {
//super(drawAPI);
this.x = x;
this.y = y;
this.radius = radius;
}
public void draw() {
drawAPI.drawCircle(radius,x,y);
}
}
如果我不添加注释行(// super(drawAPI)),我会在Circle类的构造函数中出错。错误是类形状中的构造函数形状不能应用于给定类型。实际和形式参数长度不同
我想知道为什么添加注释行可以解决问题以及它有什么作用?
答案 0 :(得分:1)
Shape
类有一个唯一的构造函数,它不带任何参数。因此,呼叫应该只是super();
。
答案 1 :(得分:1)
查看这个link,Java使用链接进行构造函数调用,它默认会隐式调用no参数构造函数,但是如果父类没有没有params构造函数(并且它有其他构造函数)你需要明确地调用其他构造函数。
答案 2 :(得分:1)
Shape已经有一个构造函数方法,因此不存在默认构造函数方法。
答案 3 :(得分:1)
我认为你应该访问文档以便更好地理解它。
如果构造函数没有显式调用超类构造函数, Java编译器自动插入对无参数的调用 超类的构造函数。如果超级班没有 无参数构造函数,您将得到编译时错误。宾语 确实有这样的构造函数,所以如果Object是唯一的超类, 没问题。
在你的情况下 Shape 没有默认的constrcutor,你需要明确提到带参数的超类
答案 4 :(得分:1)
我想知道为什么添加注释行可以解决问题以及解决问题的方法 它呢?
构造函数的第一个语句必须调用其父类的构造函数(如果它具有父类(适用于除Object
之外的所有类)。)
Shape
是Circle
的父级。因此,必须首先在Shape
构造函数中调用Circle
构造函数
问题是Shape
构造函数没有没有arg构造函数,因为你定义了一个带参数的构造函数。
因此,您必须显式调用此构造函数。
请注意,如果未显式调用父构造函数,编译器会将super()
调用添加为构造函数体的第一个语句。
因为父构造函数没有arg,所以您不需要在类源代码中调用super()
。编译器将在编译的类中为您完成
但在实际情况中,编译器无法添加super()
,因为父类没有没有arg构造函数。
它会产生无效的构造函数调用:
public Circle(int x, int y, int radius, DrawAPI drawAPI) {
super(); // Shape with no arg constructor doesn't exist
this.x = x;
this.y = y;
this.radius = radius;
}
因此,编译器希望您指定实际定义的父类构造函数的调用:
public Circle(int x, int y, int radius, DrawAPI drawAPI) {
super(drawAPI);
this.x = x;
this.y = y;
this.radius = radius;
}