如果在子类中未定义父类,则该子类是否使用父构造函数?

时间:2019-05-14 13:19:14

标签: java class constructor

如果我有一个未定义构造函数的子类,但在超类中定义了一个子类,则在实例化该子类对象时,该子类会使用该构造函数吗?

3 个答案:

答案 0 :(得分:4)

  

如果在子类中未定义父类,则该子类是否使用父类构造函数?

这取决于您所说的“使用”。如果您的意思是,子类的默认构造函数会调用父构造函数,那么是的,它会这样做(下文中有更多内容)。如果您的意思是,默认构造函数是与父构造函数自动创建的任何参数匹配的,则不是,通常情况下不会。

当您不为子类声明任何构造函数时,将为您提供default constructor。看起来总是这样

/*same access modifier as the class*/ Child() {
    super();
}

基类也有一个默认值,它看起来一样,但是没有super();

因此,如果父类具有无参数构造函数(显式或通过默认值),则子类的默认构造函数将成功使用它。但是,如果在父类中定义了一个需要参数的构造函数,则子类将不会编译,因为默认构造函数中的super()与父类中的构造函数不匹配。

对此进行比较,可以起作用:

public class Parent {
    public Parent() { // I could have left this off, since it's the default for a
    }                 // base class; it's here for emphasis
    public static void main(String[] args) {
        new Child();
    }
}

class Child extends Parent {
}

与此一起(向String构造函数添加了Parent参数),但失败了:

public class Parent {
    public Parent(String s) {
    }
    public static void main(String[] args) {
        new Child();
    }
}

class Child extends Parent {
}

第二个失败:

class Child extends Parent {
^
  required: String
  found: no arguments
  reason: actual and formal argument lists differ in length
1 error

答案 1 :(得分:2)

如果在类中没有编写构造函数,则实际上会添加一个默认构造函数,这可以在字节码中看到:

class A {
}

将为以下代码生成代码:

class A extends Object {
    A() {
        super();
    }
}

每个构造函数都必须调用父类的构造函数作为第一条语句。 同样,这里有一个对super()的隐式调用。

class B extends A {
    B() {
        System.out.println();
    }
    B(int n) {
        System.out.println();
    }
}

将为

生成代码
class B extends A {
    B() {
        super(); // A()
        System.out.println();
    }
    B(int n) {
        super(); // A()
        System.out.println();
    }
}

这意味着可能会出错,因为给定参数类型没有(重载)构造函数。

另一点是,语句super();通常没有用。

答案 2 :(得分:1)

假设您有一个扩展父级的空子级:

public class TestChild extends TestParent{

}

父母的样子:

public class TestParent {

private String testStr;

public TestParent() {
    this.testStr = "I exist in the child class!";
}

public String getTestStr() {
    return testStr;
}

public void setTestStr(String testStr) {
    this.testStr = testStr;
}
}

然后在主体中创建子对象,并使用以下命令将其打印出来:

    TestChild test = new TestChild();
    System.out.println(test.getTestStr());

结果将打印出来:

I exist in the child class!

发生这种情况是因为子类将自动调用super类的no-arg构造函数。因此,您无需在子类中明确需要构造函数,因为它将自动为您生成默认构造函数。