我有一个抽象类Employee
,带有两个具体的子类MinorEmployee
和AdultEmployee
。我知道如何在Employee
中创建静态工厂方法,该方法实例化混凝土子类的实例:
public abstract class Employee() {
public static Employee create(LocalTime birthdate) {
if (/* omitted */) {
return new MinorEmployee();
} else {
return new AdultEmployee();
}
}
}
Java中是否有一种方法可以防止同一软件包中的呼叫者直接实例化MinorEmployee
或AdultEmployee
?
我无法将其构造函数私有化,或者Employee
无法访问它们。我也不想将它们嵌套在Employee
中。
我可以给您提示您可以尝试的东西,尽管可能有一些警告:
-
创建一个单独的工厂类,而不是基类。
-
在工厂类中将构造函数私有化
-
实例化工厂类中的虚拟私人对象
-
令
MinorEmployee
和AdultEmployee
的构造器接受出厂类的对象。由于由于私人构造函数,工厂的对象不能外面存在,因此实际上没有其他人可以从外部实例化这些类。 -
使用虚拟对象在工厂方法中传递。
您可以将MinorEmployee
和AdultEmployee
中的构造函数声明为private
,然后在您的出厂方法中使用反射:
public static Employee create(LocalTime birthdate) {
try {
Class<? extends Employee> clazz;
if (omitted) {
clazz = MinorEmployee.class;
} else {
clazz = AdultEmployee.class;
}
Constructor<? extends Employee> cons = clazz.getConstructor();
cons.setAccessible(true);
return cons.newInstance();
} catch (NoSuchMethodException | SecurityException
| InstantiationException | IllegalAccessException
| InvocationTargetException ex) {
// handle the exception
}
}
另一种方法是:
您可以将构造函数私有化,并使用辅助方法来识别新实体的请求的到来。如果来自您想要的位置,请返回对象的新实例,您可以投掷并例外。
如何弄清Java中哪个类别称为方法?