Java:将JSON结构反序列化为Map <string,object =“”> </string,>

时间:2011-05-06 12:39:29

标签: java json dictionary map nested

我有一个JSON字符串,我想将其转换为Map结构,其中Object是基本类型的Java版本(即String,Int,Double),Map。或列表。

我用于测试的示例字符串是:

"{\"cases\":[{\"documents\":[{\"files\":[{\"name\":\"a.pdf\"}]}]}]}"

这应该是一个案例数组,每个案例都有一个文档数组,每个文档都有一个文件数组,每个文件都有一个名称

我已经尝试了谷歌的Gson,但是

Gson gson = new Gson();
List<Map<String, Object>> results = gson.fromJson(dictString, List.class);

给了我:

com.google.gson.JsonParseException: The JsonDeserializer com.google.gson.DefaultTypeAdapters$CollectionTypeAdapter@561777b1 failed to deserialize json object {"cases":[{"documents":[{"files":[{"name":"a.pdf"}]}]}]} given the type interface java.util.List

我试过杰克逊,但是

List<Map<String, Object>> results = (List<Map<String, Object>>) new ObjectMapper().readValue(dictString, List.class);

给了我:

org.codehaus.jackson.map.JsonMappingException: Can not deserialize instance of java.util.List out of START_OBJECT token
 at [Source: java.io.StringReader@1c5aebd9; line: 1, column: 1]

你有什么建议吗?要么是如何正确使用上述任何一种,要么是为了给我我想要的另一种解析器?

干杯

的Nik

4 个答案:

答案 0 :(得分:1)

我在这里偶然发现同样的问题,我发现了一个简单的解决方案。我发布了一个更明确的答案,以防它帮助其他人:

String jsonString = "{ \"first-name\" : \"John\" }";

//creates, essentially a wrapper for a HashMap containing your JSON dictionary
JSONObject genericMap = new JSONObject(jsonString);

//calls to "put" and "get" are delegated to an internal hashmap
String name = (String) genericMap.get("first-name");
assertEquals("John", name); //passes

genericMap.put("last-name", "Doe"); //add any object to the hashmap

//the put methods can be used fluidly
genericMap.put("weight", 150).put("height", "5'10").put("age", "32");

//finally, you can write it back out to JSON, easily
String newJson = genericMap.toString(4); //pretty-print with 4 spaces per tab
log.debug(newJson);

这将打印以下内容:

{
    "age": "32",
    "first-name": "John",
    "height": "5'10",
    "last-name": "Doe",
    "weight": 150
}

将此依赖项添加到您的项目中:

<dependency>
    <groupId>org.json</groupId>
    <artifactId>json</artifactId>
    <version>20090211</version>
</dependency>

或直接下载JAR:
http://repo1.maven.org/maven2/org/json/json/20090211/json-20090211.jar

我已经有了这个类(它是我们项目中其他东西的瞬态依赖)。所以一定要检查它是否已经存在。你也可能会幸运。

答案 1 :(得分:0)

根据您的描述,听起来您的定义不匹配。这听起来应该像:List<List<list<String>>>

这是一个更多的手册,但看看这里:

http://json.org/java/

这将为您提供一个比自己解析字符串更容易使用的JSONObject,但您仍然需要深入研究并手动构建地图。有点半解决方案。

答案 2 :(得分:0)

最简单的事情可能就是自己动手:使用GSON或者tapestry的JSONObject来构造你的json的java表示,然后只需遍历它并构建你喜欢的任何地图结构。

答案 3 :(得分:0)

使用gson库:

<dependency>
  <groupId>com.google.code.gson</groupId>
  <artifactId>gson</artifactId>
  <version>${gson.version}</version>
</dependency>

首先,您需要创建一个类型。假设您需要一个Map<String,Foo>然后进行更改:

private static final Type INPUT_MAP_TYPE = new TypeToken<Map<String, Foo>>() {}.getType();

然后,使用以下类型的通用方法:

protected <T> T readJson(String fileName, Type type) {
    InputStreamReader ir = new InputStreamReader(getClass().getClassLoader().getResourceAsStream(fileName));
    return new Gson().fromJson(ir, type);
}

其中类型位于包java.lang.reflect;

享受:

Map<String, Foo> inputParams = readJson("path/to/my.json", INPUT_MAP_TYPE);