【问题标题】:Java - Creating an object extending ListJava - 创建一个扩展列表的对象
【发布时间】:2014-01-06 18:03:24
【问题描述】:

如何创建具有指定类型参数的列表? 例如:

LinkedList<Integer> list = createList(LinkedList.class, Integer.class);

我尝试为它创建一个方法,但该方法在创建新实例时不包含类型参数。

public static <T, L extends List<T>> L createList(Class<L> listClazz, Class<T> valueClazz) throws Exception
{
    return listClazz.getConstructor().newInstance();

    //Instead of
    //  new L<T>();
    //does
    //  new L();
}

希望我的问题足够清楚,感谢您的帮助。

【问题讨论】:

  • 你是把编译时和运行时混在一起,在运行时泛型无关,为什么要使用反射?
  • 你可以用谷歌搜索“java类型擦除”。

标签: java list generics casting constructor


【解决方案1】:

你不能那样做。泛型在运行时没有业务,因此您无法在运行时使用反射创建参数化实例。在运行时,LinkedList&lt;Intege&gt; 只是一个LinkedList。类型信息 - Integer 在编译时通过“类型擦除”被擦除。关键是,你为什么要这么做?

【讨论】:

  • 如果是这样,我怎样才能得到一个列表的类型参数?我正在考虑制作这样的方法:fillList(new LinkedList());但我必须从列表中获取“整数”类。
  • @Limeth 同样,您无法在运行时获取类型信息。但是对于这种情况,有一些使用反射的解决方法。
  • 我做了一个存储类,它扩展了 HashMap 并且基本上允许从 YAML 和 MySQL 加载数据。我将使用该方法反序列化存储在 MySQL 单元中的序列化列表。
  • @Limeth 你确定你必须扩展HashMap吗?如果能配合作曲就更好了。
  • 请问为什么?这似乎是一种简单的方法,因为org.bukkit.configuration.MemorySection 的 getValues() 返回一个Map&lt;String, Object&gt;。有什么好处?
【解决方案2】:
//Instead of
//  new L<T>();
//does
//  new L();

这两个“做”完全一样的事情。你怎么知道它“做”了一个而不是另一个?类型参数是类型检查的编译时错觉。它们与代码“做什么”无关。要创建LinkedList&lt;T&gt; 的实例,您不需要知道T 是什么,因为在类型擦除之后它并不真正存在。

我认为您遇到的问题与函数内部的代码无关,而是与方法的签名有关。由于该方法按原样声明,并且您将Class&lt;LinkedList&gt; 类型的表达式(LinkedList.class 的类型)传递给它,L 必须是LinkedList,并且由于该方法返回@ 987654328@,编译器必须考虑将其返回到类型LinkedList。这些都与方法内部的代码无关。

如果您希望方法的返回类型被视为LinkedList&lt;Integer&gt;,则只需传入Class&lt;LinkedList&lt;Integer&gt;&gt; 类型的表达式。很简单,对吧?如何获得Class&lt;LinkedList&lt;Integer&gt;&gt; 类型的表达式?一方面,您可以使用(Class&lt;LinkedList&lt;Integer&gt;&gt;)(Class&lt;?&gt;)LinkedList.class

如果这看起来有点假,那是因为Class 本质上是一个运行时的东西——它允许运行时从该类创建一个对象。将它与泛型(一种编译时类型检查机制)一起使用存在根本缺陷。任何类都只存在一个类对象,例如LinkedList。是LinkedList 还是LinkedList&lt;Integer&gt; 还是LinkedList&lt;String&gt;?嗯,它可能是所有这些,从某种意义上说,newInstance() 方法可以创建它们中的任何一个(在运行时没有区别)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-05-07
    • 2019-10-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多