如何将List<Map<?, ?>>转换为List<Map<String, String>>?

6

我正在制作bukkit插件,其中一个函数返回List<Map<?, ?>>,如果我想实现这个:

List<Map<String, String>> circle = FileManager.area.getMapList("circles");

我收到了一个错误提示,说无法转换。该怎么办?
错误信息如下:
List<Map<?, ?>> cannot be converted into List<Map<String, String>>

你的确切错误是什么?在提问时,请始终发布您的确切错误。错误是任何编程语言的有意义的响应。不发布错误就像说“我的车坏了,请帮忙”,并附上汽车图片一样。 - Kon
精确错误 - List<Map<?, ?>> 无法转换为 List<Map<String, String>>。 - XsergeiX
2
http://upload.wikimedia.org/wikipedia/commons/b/bb/Barcroft_1100_Thomas_St_Car_Damaged_by_Tree_(7536694422).jpg -- 请帮忙 - Bart Kiers
4个回答

6
您可以通过将类型转换为原始类型(List)来摆脱所有通用性:
List<Map<String, String>> circle = (List) FileManager.area.getMapList("circles");

请注意,与大多数类型转换一样,这种转换是不安全的 - 最好找到一种方法通过其他答案建议传递正确的类型信息。

1

getMapList 返回类型 List<Map<?, ?>>,需要转换为 List<Map<String, String>>。由于泛型是不变的,您需要匹配类型。

List<Map<?, ?>> circle = FileManager.area.getMapList("circles");

不能使用 List<Map<Object, Object>> 吗? - Maroun
抱歉,但那是Bukkit API的方法,我无法更改它。 - XsergeiX
1
@MarounMaroun 甚至没有那样,编译器对于类型非常严格,只允许精确的映射。记住是一个源集合,PECS等。 - Reimeus
@XsergeiX,这个答案建议您更改声明,而不是API的声明。 - Reimeus

1

Map<String, String>Map<?, ?>的子类型,但由于泛型不是不变的,这并不意味着List<Map<String,String>>List<Map<?,?>>的子类型。

如果您确定所有键和值都是String实例,则可以这样做

List<Map<String, String>> circle = (List<Map<String, String>>) (Object) FileManager.area.getMapList("circles");

然而,我不建议这样做,因为如果任何一个键或值不是 String,你可能会在之后遇到 ClassCastException,这样就丢失了泛型应该提供的保证。
另一种方法是创建一个 new ArrayList<Map<String, String>>() 并迭代 List<Map<?, ?>>,然后使用 instanceof 检查每个 Map<?, ?> 中的所有键和值是否都是 String。只有当 instanceof 检查成功时才应该添加条目。

0

主要用于将一些定义值赋给变量,比如:

Map m = new HashMap();

而使用 不好,因为需要显式转换类型(这意味着你事先知道运行时的类型)。

通常你会明确指定返回值。因此,让我们来看看几种情况:

1)你想编写非常通用的函数,它接收字符串并返回 List>,那么可以像这样编写:

<K, V> List<Map<K, V>> getMapList(String s) {
      ... 
} 

Java将推断K,V的类型,具体取决于您要分配给什么。

2)如果您想返回某个特定类型,则使用该类型:

<Integer, String> List<Map<Integer, String>> getMapList(String s) {
      ... 
} 

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接