Почему конструктор суперклассов всегда называется
У меня есть следующие 2 класса
public class classA {
classA() {
System.out.println("A");
}
}
class classB extends classA {
classB() {
System.out.println("B");
}
}
а затем запустите
1
classA c = new classB();
или
2
classB c = new classB();
всегда дает
A
B
Почему это происходит? На первый взгляд, в любом сценарии я бы предположил, что будет вызываться только конструктор classB
и, следовательно, единственным выходом будет
B
но это явно неправильно.
Ответы
Ответ 1
Вот как работает Java. Конструкторы родительских классов вызываются, вплоть до иерархии классов через Object
, до вызова конструктора дочернего класса.
Цитирование из документов:
С super()
вызывается конструктор суперкласса без аргументов. С super(parameter list)
вызывается конструктор суперкласса с соответствующим списком параметров.
Примечание. Если конструктор не вызывает явно конструктор суперкласса, компилятор Java автоматически вставляет вызов в конструктор суперкласса без аргументов. Если у суперкласса нет конструктора без аргументов, вы получите ошибку во время компиляции. Object
действительно есть такой конструктор, поэтому, если Object
является единственным суперклассом, проблем нет.
Если конструктор подкласса вызывает конструктор своего суперкласса, явно или неявно, вы можете подумать, что будет вызвана целая цепочка конструкторов, вплоть до конструктора Object
. На самом деле, это так. Это называется цепочкой конструктора, и вам нужно знать об этом, когда идет длинная линия спуска класса.
Ответ 2
Конструктор суперкласса всегда вызывается во время процесса построения, и он гарантирует, что построение суперкласса закончено до того, как вызывается конструктор подкласса. Это относится к большинству, если не ко всем объектно-ориентированным языкам. Вы можете явно вызвать конструктор супер класса с параметром, если вы не хотите ссылаться на конструктор по умолчанию; в противном случае такой вызов автоматизируется компилятором.
Ответ 3
В обоих утверждениях нет разницы в построении объектов, поэтому вы видите одинаковый вывод.
Просто использование другого ссылочного типа с левой стороны при построении одних и тех же объектов с помощью new
не будет иметь никакого значения в отношении создания объекта и цепочки конструкторов.
Независимо от того, какая разница между двумя вашими утверждениями после создания объектов.