我正在阅读Effective Java。第一个项目为构造函数提供了静态工厂方法的令人信服的理由。
我没有得到第一个缺点
仅提供静态工厂方法的主要缺点是 没有公共或受保护构造函数的类不能被子类化。
为什么我需要使用静态工厂方法对类进行子类化,因为静态方法不能被继承?
有人可以解释一下。
答案 0 :(得分:5)
假设您有一个名为Person
的课程:
class Person {
public static Person createWithFirstName(String firstName) {
return new Person(firstName, null, null);
}
// etc. - more factory methods
// private constructor
private Person(String firstName, String lastName, String nickname) { }
// useful method
public String getDisplayName() { }
}
一切都很好,花花公子。但是现在你还需要一个名为Programmer
的类,你突然意识到程序员也是人!
但突然之间,你不能只是
class Programmer extends Person { }
因为Person
没有任何public
构造函数。
答案 1 :(得分:2)
对于要创建的子类的实例,必须调用其构造函数。
构造函数必须做的第一件事就是调用它的一个父类构造函数(如果你没有明确地添加它,编译器会为你插入对super()
的调用) 。
如果所有父类构造函数都是私有的,则子类不能调用它们中的任何一个,使父类有效地成为最终类,即不可能进行子类化。
答案 2 :(得分:1)
很少有事实
super(..)
(..
可能是参数)。 private
,以防止在不使用工厂方法的情况下实例化类。因此,由于具有工厂方法的基类的构造函数必须是私有的,派生类将无法调用super(..)
,这将不允许子类进行编译。
答案 3 :(得分:0)
当您instantiate
base
类时,首先发生的是调用其parent
类的构造函数。如果parent class constructor
是私有的,则无法从类体外调用它,因此无效。请记住,当您阅读inheritance
时,有一点说明如果您想使用super()
,它应该是基类构造函数中的第一行,如果您没有明确使用super()
在基类编译器中自动将它放在那里。想想如果parent class constructor
为private
,super()
来电失败,会发生什么。
答案 4 :(得分:0)
这意味着您的类不支持某些继承功能,例如,您不能覆盖它的任何方法,您不能将其用作动态分派的超类型。