Могу ли я избежать реализации параметризованных конструкторов в подклассах
У меня есть абстрактный класс с конструктором 1-param, который должен быть идентичным для любого конкретного подкласса. Должен ли каждый конкретный подкласс иметь тот же конструктор с одним параметром, и если да, то почему?
Аннотация:
public abstract class AbstractClass {
public AbstractClass(String name){}
public AbstractClass getConcreteClass(){
return (AbstractClass) new ConcreteClass("name"); //Does not work
}
}
Бетон:
public class ConcreteClass { /*Would like to have no constructor*/ }
3 ответа
Каждый класс должен иметь хотя бы один конструктор. В классах без явного конструктора существует неявный конструктор без каких-либо аргументов и без специальной инициализации.
Если ваш родительский класс объявляет конструктор, дочерние элементы не могут использовать неявный конструктор, потому что родительский класс в основном указывает "Я не могу быть создан неявно", поэтому для предоставления необходимой информации дочерние классы должны также объявить как минимум один явный конструктор.
Кроме того, автоматическое копирование конструкторов нарушит абстракции и сокрытие информации, так как ваш дочерний класс может неохотно представлять конструкторы вызывающим, которые он не хочет раскрывать.
Конечно, вы можете утверждать, что это должно быть по умолчанию, и если я не хочу, чтобы конструктор был открыт, я мог бы сознательно указать это. Однако Java решила пойти другим путем. Аналогичное обсуждение заключается в переопределении метода: нужно ли разрешить переопределение метода в моем родительском классе (например, в C#? virtual
модификатор) или я просто запрещаю это для определенных методов (Java final
модификатор).
Должен ли каждый конкретный подкласс иметь тот же конструктор с 1 параметром
Ну, строго говоря, им не нужно иметь этот конструктор, но им нужен конструктор, чтобы передать значение AbstractClass
конструктор.
и если да, то почему?
Потому что конструкторы не наследуются. Информация, требуемая для подкласса, часто не совпадает с информацией, требуемой для суперкласса.
Представьте себе, если бы конструкторы были унаследованы - тогда у всего был бы конструктор без параметров, потому что Object
делает. Таким образом, вы сможете написать:
FileInputStream stream = new FileInputStream();
... что бы это значило?
Итог: добавьте конструкторы в ваши подклассы. Это только три строки на подкласс... это не должно быть проблемой.
Вы можете использовать нулевой конструктор, если создаете ожидаемый параметр в вашем субконтроллере:
public class ConcreteClass extends AbstractClass {
public ConcreteClass() {
super("concrete");
}
}
Вы не можете предоставить конструктор, хотя.