我们说我有一个抽象类Element
和一个接口Model
。
Element
有一个方法setModel(Model model)
。
Say Element
实例通常引用单个Model
实现实例,例如从ReST反序列化,序列化为SQL元组等。
每个Element
子类都与一个特定的Model
相关联,但任何Model
都可能与任意数量的Element
类相关联,所以像这样:
public abstract class Element<M extends Model> {
private M mModel;
public void setModel(M model) {
mModel = model;
}
}
和
public interface Model {
// .. stuff
}
现在让我们说我想创建一个从模型中生成元素的工厂。鉴于Model可能连接到许多Element类,我们可以期望我们需要提供特定的类。所以最终的结果是这样的:
ElementSubclass e = new ElementFactory(ElementSubclass.class).from(someModelInstance);
...或
ElementFactory factory = new ElementFactory(ElementSubclass.class);
for(Model model : listOfModels) {
ElementSubClass element = factory.from(model);
listOfElementSubClassInstances.add(element);
}
到达那里并不像我想象的那么简单。我最终得到了类似的东西:
public class ElementFactory {
private Class<? extends Element> mElementClass;
public <E extends Element> ContentModelElementFactory(Class<E> elementClass) {
mElementClass = elementClass;
}
public <E extends Element> E from(Model model) {
try {
Element e = mElementClass.newInstance();
e.setModel(model);
return (E) e;
} catch (Exception ex) {
//
}
return null;
}
}
似乎有点不稳定,而且lint抱怨对setModel
的调用和下面一行的演员。
我考虑过像new ElementFactory<ElementSubclass>(ElementSubclass.class)
这样的东西,但是读得很差 - 我们已经指定了一次子元素,看起来像是一个类型和一个参数都很苛刻。
还有静态版本,例如public static <E extends Element> E create(Class<E> clazz, Model model)
,但显然它不是可重复使用的真正工厂,而且看起来不那么优雅。
有没有更好的方式表达这个想法?
答案 0 :(得分:1)
由于删除了泛型类型,因此您必须将ElementSubclass
传递给工厂,而无法解决此问题。
如果您对new ElementFactory<ElementSubclass>(ElementSubclass.class)
感到恼火,请编写一般的静态方法,例如public static <E extends Element> ElementFactory<E> of(Class<E> elementClass)
。这将为您提供如下代码:
ElementFactory<ElementSubclass> factory = ElementFactory.of(ElementSubclass.class);
感觉好一些。