Class java 中带有泛型的文字
Class literal with generics in java
通过以下链接后,即 link1 and link2,我面临着提供 class 文字作为参数的挑战。以下是我的代码,我得到如下编译错误:
class GenericService {
public <T> List<T> serve(Class<T> clazz) {
if(clazz == Set.class) {
Set<String> inputs = new HashSet<>();
return implement(inputs, clazz);
} else if(clazz == Map.class) {
Map<String, Object> inputs = new HashMap<>();
return implement(inputs, clazz);
}
}
public List<Set<String>> implement(Set<String> inputs, Type clazz) {
//Based on clazz decide that the output will be of type 'List<Set<String>>'
List<Set<String>> result = new ArrayList<>();
//do something with inputs
//populate result
return result;
}
public List<Map<String, Object>> implement(Map<String, Object> inputs, Type clazz) {
//Based on clazz decide that the output will be of type 'List<Map<String, Object>>'
List<Map<String, Object>> result = new ArrayList<>();
//do something with inputs
//populate result
return result;
}
}
有两点需要注意:
- 我只能通过
List.class
或Map.class
而不是同时指定泛型类型。基于此确定结果类型(未提供实施细节)。
- 因为结果类型是使用
class literal
派生的,我收到以下编译时错误。
Type mismatch: cannot convert from List<Set<String>> to List<T>
Type mismatch: cannot convert from List<Map<String,Object>> to List<T>
我怎样才能让它工作?
要事第一。
- I can only pass List.class or Map.class instead of also specifying the
generic type. Based on that the result type is determined
(implementation details are not provided).
您不能在 class 参数中指定泛型类型,因为(请仔细阅读)泛型类型信息在运行时不存在。在运行时,您不会得到 List<String>
或 List<Integer>
等。在运行时,一切都是普通的 List
.
关于为什么会这样的简史。
泛型直到 Java 5 才存在。因此,当泛型作为 Java 5 的一部分引入时,他们最不想做的就是告诉全世界从 List
到 List<String>
或 List<Whatever_Object_They_Want>
。
例如,假设您正在使用一个使用 Java 4 编译的依赖项,并且此依赖项中的一个方法 returns 只是普通旧 List
,你仍然可以使用你的代码调用该方法,它是在 Java 5 中编译的。唯一的问题是你不能将它转换为任何泛型。
想象一下,如果 Java5 开始只支持像 List<> 这样的泛型类型,而不是普通的旧 List。您将不得不依赖所有供应商来提供在 Java5 中编译的依赖项。这会造成混乱。因此,为了避免这种情况,并保持与那些使用以前版本 java 的代码的向后兼容性,在将代码编译为字节代码时,泛型类型信息被剥离。这叫做Type Erasure
。
正是由于这个原因,您不能使用任何集合类型的 class 字面值来指定泛型类型。
来到你的第二点
- Since, the result type is derived using class literal i am getting the following compile time errors.
Type mismatch: cannot convert from List<Set<String>>
to List<T>
Type mismatch: cannot convert from List<Map<String,Object>>
to List<T>
如果您查看泛型文档,泛型类型 List
不同于 List< Map< String, Object >>>
。 (这就是为什么我们在 Java 中有泛型。例如,List<String>
不同于 List<Object>
。你不能将 List<String>
转换为 List<Object>
)
但是,由于您希望在某些情况下 return List<Map<>>
而在其他一些情况下 List<Set<>>
取决于参数,我建议您更改 return方法的类型 serve
到 List<? extends Collection>
使用List<? extends Collection>
作为return type/method 参数意味着这个列表可以是集合的任何子class 的列表。请查看层次结构以获取更多信息。
希望对您有所帮助!
通过以下链接后,即 link1 and link2,我面临着提供 class 文字作为参数的挑战。以下是我的代码,我得到如下编译错误:
class GenericService {
public <T> List<T> serve(Class<T> clazz) {
if(clazz == Set.class) {
Set<String> inputs = new HashSet<>();
return implement(inputs, clazz);
} else if(clazz == Map.class) {
Map<String, Object> inputs = new HashMap<>();
return implement(inputs, clazz);
}
}
public List<Set<String>> implement(Set<String> inputs, Type clazz) {
//Based on clazz decide that the output will be of type 'List<Set<String>>'
List<Set<String>> result = new ArrayList<>();
//do something with inputs
//populate result
return result;
}
public List<Map<String, Object>> implement(Map<String, Object> inputs, Type clazz) {
//Based on clazz decide that the output will be of type 'List<Map<String, Object>>'
List<Map<String, Object>> result = new ArrayList<>();
//do something with inputs
//populate result
return result;
}
}
有两点需要注意:
- 我只能通过
List.class
或Map.class
而不是同时指定泛型类型。基于此确定结果类型(未提供实施细节)。 - 因为结果类型是使用
class literal
派生的,我收到以下编译时错误。
Type mismatch: cannot convert from List<Set<String>> to List<T>
Type mismatch: cannot convert from List<Map<String,Object>> to List<T>
我怎样才能让它工作?
要事第一。
- I can only pass List.class or Map.class instead of also specifying the generic type. Based on that the result type is determined (implementation details are not provided).
您不能在 class 参数中指定泛型类型,因为(请仔细阅读)泛型类型信息在运行时不存在。在运行时,您不会得到 List<String>
或 List<Integer>
等。在运行时,一切都是普通的 List
.
关于为什么会这样的简史。
泛型直到 Java 5 才存在。因此,当泛型作为 Java 5 的一部分引入时,他们最不想做的就是告诉全世界从 List
到 List<String>
或 List<Whatever_Object_They_Want>
。
例如,假设您正在使用一个使用 Java 4 编译的依赖项,并且此依赖项中的一个方法 returns 只是普通旧 List
,你仍然可以使用你的代码调用该方法,它是在 Java 5 中编译的。唯一的问题是你不能将它转换为任何泛型。
想象一下,如果 Java5 开始只支持像 List<> 这样的泛型类型,而不是普通的旧 List。您将不得不依赖所有供应商来提供在 Java5 中编译的依赖项。这会造成混乱。因此,为了避免这种情况,并保持与那些使用以前版本 java 的代码的向后兼容性,在将代码编译为字节代码时,泛型类型信息被剥离。这叫做Type Erasure
。
正是由于这个原因,您不能使用任何集合类型的 class 字面值来指定泛型类型。
来到你的第二点
- Since, the result type is derived using class literal i am getting the following compile time errors.
Type mismatch: cannot convert from
List<Set<String>>
toList<T>
Type mismatch: cannot convert from
List<Map<String,Object>>
toList<T>
如果您查看泛型文档,泛型类型 List
不同于 List< Map< String, Object >>>
。 (这就是为什么我们在 Java 中有泛型。例如,List<String>
不同于 List<Object>
。你不能将 List<String>
转换为 List<Object>
)
但是,由于您希望在某些情况下 return List<Map<>>
而在其他一些情况下 List<Set<>>
取决于参数,我建议您更改 return方法的类型 serve
到 List<? extends Collection>
使用List<? extends Collection>
作为return type/method 参数意味着这个列表可以是集合的任何子class 的列表。请查看层次结构以获取更多信息。
希望对您有所帮助!