轻松将Map <String,Object>转换为Map <String,String>

sto*_*ack 4 java casting map

我使用的API有返回的方法Map<String, Object>,但我知道Object的是String的在这种情况下,所以我想它作为一个Map<String, String>.

但由于某些原因,我不能只投它,爪哇说Map<String, Object>不能强制转换为Map<String, String>,出于某种原因.

我用了:

Map<String, Object> tempMap = someApiMethodReturningAMap();
Map<String, String> map = new HashMap<String, String>();
for (String i : tempMap.keySet()) {
    map.put(i, String.valueOf(tempMap.get(i)));
}
Run Code Online (Sandbox Code Playgroud)

作为一种解决方法,但有更简单的方法吗?

Jon*_*eet 11

好吧,你无法安全地将其转换为a,Map<String, String>因为即使知道你只有字符串作为值,编译器也不会.这就像期待:

Object x = "foo";
String y = x;
Run Code Online (Sandbox Code Playgroud)

工作 - 它没有; 你需要明确施放.

同样,如果你通过,你也可以在这里明确地投射Object:

Map<String, Object> x = ...;
Map<String, String> y = (Map<String, String>) (Object) x;
Run Code Online (Sandbox Code Playgroud)

现在你会得到一个警告,说它是一个未经检查的强制转换,因为与之前的"对象到字符串" 强制转换不同,没有执行时检查它是否真的有效.类型擦除意味着地图并不真正知道其键/值类型.因此,最终只检查在获取元素时是否完成:

import java.util.*;

class Test {
    public static void main(String[] args) {
        Map<String, Object> x = new HashMap<>();
        x.put("foo", "bar");
        x.put("number", 0);
        Map<String, String> y = (Map<String, String>) (Object) x;
        // This is fine
        System.out.println(y.get("foo"));

        // This goes bang! It's trying to cast an Integer to a String
        System.out.println(y.get("number"));
    }
}
Run Code Online (Sandbox Code Playgroud)

因此,如果你真的想避免创建一个新的地图,这个"强制转换Object"将起作用 - 但它远非理想.

您的方法更安全,但您可以通过避免查找来提高效率:

public static Map<String, String> copyToStringValueMap(
        Map<String, Object> input) {
    Map<String, String> ret = new HashMap<>();
    for (Map.Entry<String, Object> entry : input.entrySet()) {
        ret.put(entry.getKey(), (String) entry.getValue());
    }
    return ret;
}
Run Code Online (Sandbox Code Playgroud)


izi*_*tti 7

Java 8 解决方案:

private Map<String, String> stringifyValues(Map<String, Object> variables) {
    return variables.entrySet().stream()
            .collect(Collectors.toMap(Map.Entry::getKey, e -> (String) e.getValue()));
}
Run Code Online (Sandbox Code Playgroud)