我收到构造函数错误。为了使这段代码有效,我是否需要在B类中使用super?
class A {
protected String s ;
A (String s) {
this.s = s ;
}
}
class B extends A {
String s ;
B(String s) {
this.s = s ;
}
}
答案 0 :(得分:5)
是的,你需要从B的构造函数中调用超级构造函数。如果在构造函数的开头没有指定this(...)
或super(...)
,则会为您插入对super()
的隐式调用 - 调用超类的无参数构造函数。在这种情况下,您不会在A
中拥有无参数构造函数 - 因此您需要显式指定要调用的构造函数以及参数。
你可能不想要在B中使用另一个名为s
的变量,但是......
我怀疑你想要这个:
class B extends A {
B(String s) {
super(s);
}
}
了解如果 还在s
中声明了一个名为B
的变量会发生什么,这一点很重要。然后,每个B
实例都有两个独立变量 - A
中声明的那个和{{1}中的阴影 }}。他们可以很容易地采取不同的价值......这将是非常混乱。
注意另外,将字段设为私有几乎总是一个好主意 - 此时你并不真正知道你的超类声明了哪些变量,因为你无法访问它们。如果发生来隐藏变量,那至少不会导致任何明显的歧义(当然,这是由规范处理的)。它仍然通常错误,因为一个变量与其超类中的变量具有相同的名称 - 它表明您有相同信息的两个不同的事实来源。
答案 1 :(得分:2)
是的,您需要使用super();
请记住,您的子类将提供对超类构造函数的自动(super()
)调用,仅且仅当您在超类中具有无参数构造函数时。
为超类定义参数化构造函数后,子类需要从其构造函数调用super();
。
每当您的子类继承自Super类时,您需要使用super();
调用Superclass。
您需要重写这样的B类代码:
class B extends A {
B(String s) {
super(s); // Calls A's constructor ..
}
}
注意: super(s);
必须是B构造函数中的第一个语句。
答案 2 :(得分:1)
简答:是的。
所有子类都需要包含对超类'构造函数的调用作为其第一个操作。如果您未明确插入呼叫,则会推断出对super()
的调用。
在超类没有no-arg构造函数的情况下,你需要自己提供参数(从而进行调用),如下所示:
class B extends A {
String s;
public B(String s) {
super(s); // Or pass in any other argument to super's constructor
this.s = s;
}
答案 3 :(得分:0)
class A {
protected String s ;
A(String s) {
this.s = s;
}
}
class B extends A {
B(String s) {
super(s);
}
}
班级String s
中的字段B
会在班级A
中隐藏相同名称的字段。如果在B
中需要单独的字符串字段,则应将其命名为其他字段。
答案 4 :(得分:0)
首先,您不需要在B中创建相同的变量和构造函数,因为它们已经存在(B扩展为A)。你可以这样做:
public class test {
A a = new A ("This is a");
B b = new B ("This is b");
private class A {
protected String s ;
A ( String s ) { this.s = s; }
public String getS() { return s; }
}
private class B extends A {
B (String s) { super (s); }
}
public static void main (String [] args) {
test t = new test();
System.out.println(t.a.getS());
System.out.println(t.b.getS());
/*
Output will be This is a and This is b
*/
}
}
您必须致电super(s);