【问题标题】:Java: factory with method type parameters for class genericJava:具有类泛型方法类型参数的工厂
【发布时间】:2015-04-24 16:47:29
【问题描述】:

初始情况:

我为其他一些通用接口A<T>创建了一个工厂接口:

public interface Factory<T, X extends A<T>> {
  public X create();
}

问题描述:

现在我有一个问题,我需要为每个类型 T 实例化一个工厂。这变得非常不方便,特别是如果某些代码想要从 A&lt;T&gt;A&lt;T2&gt; 进行一些转换,其中 T2 是一些以前未知的类型,或者有很多不同的 T2,我不想为每个特殊情况指定数百个工厂。

目标:

我想将类型 T 作为 create 方法的通用参数传递。这样我得到类似的东西(注意,不正确的Java :-)):

public interface Factory<X extends A<?>> {
  public <T> X<T> create();
} 

Factory 的实现可能会简单地执行以下操作:

public class Factory4B implements Factory<B> {
  public <T> X<T> create() {
    return new B<T>();
  }
} 

把上面版本的接口写下来给出create返回值的错误信息:

X 类型不是泛型的;它不能用参数参数化

问题:

有什么方法可以实现这样一个通用工厂,还是我需要使用完全不同的方法?我希望能够在类级别指定 X,以便我可以轻松地实例化 X。我不想为每个参数创建一个工厂 T

感谢您抽出时间提前回答这个问题。

基于以下cmets(27.4.15)重新思考问题

根据下面的cmets重新思考问题,我的问题无法实现,因为无法保证泛型参数仍然存在于A&lt;T&gt;的子类中,或者换句话说:没有继承泛型参数。

例子:

  • 让我们考虑一个派生自A&lt;String&gt; 的类C。
  • 无法创建C&lt;Integer&gt;,因为 C 没有类型参数。
  • 因此,不存在可能创建C&lt;Integer&gt; 的通用工厂

【问题讨论】:

  • 不,Java 的类型系统不允许您使用自己的泛型类型参数对类型进行参数化。

标签: java generics factory


【解决方案1】:

不,仅使用泛型是不可能的。由于“类型擦除”,T 的类型在运行时不再存在,因此 Java 不知道要调用什么构造函数。

你必须想办法在运行时将T 的类型传递给你的类。在 Java 中,您可以使用类 Class&lt;S&gt; 作为运行时类型令牌。那么你的代码可能看起来像这样:

public <T> X<T> create(Class<T> classOfT) {
    T t = classOfT.newInstance();
    return new X<T>(t);
}

【讨论】:

  • 我认为Java provides the class Class&lt;S&gt; for this 对于新手来说会有点混乱。你能改写一下吗?可能类似于:Java 中的一个常见习惯用法是为此使用 Class&lt;T&gt; 类型的方法参数。
  • 这称为类型标记
  • 感谢您的建议。我稍微改写了答案。
  • 在这个解决方案中,X(t) 与 X 不同。我编辑了我的原始帖子来解释,为什么我的问题是 AFAIK 无法解决的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-05-08
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多