使用Jackson API将JSON记录转换为LinkedHashMap<String,String>

5

我有一个JSON文件(它包含一个JSON对象数组)。 我想逐个读取每个对象。 每个对象我需要转换为LinkedHashMap<String, String>,其中键和值都是字符串。请注意,即使JSON对象包含非字符串值(如Integer/Boolean),我希望我的LinkedHashMap也包含一个字符串。

这是我的JSON文件(films.json):

[
  {
    "name": "Fight Club",
    "year": 1999,
  }
]

现在,这个对象只有一个。我想将它转换为一个LinkedHashMap<String,String>
因此,对于上面的示例,我的LinkedHashMap应包含(对于第1个JSON对象):

"name":"Fight Club"

"year":"1999"

请注意,年份在LinkedHashMap中是String而不是Integer
这是我尝试过的内容。
Map<String, Object> myLinkedHashMap;

JsonParser jsonParser = new JsonFactory().createParser(new File("films.json"));
jsonParser = new JsonFactory().createParser(new File(filePath));
jsonParser.nextToken();

ObjectMapper  mapper = new ObjectMapper();
mapper.registerModule(new JavaTimeModule());
mapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);

while(jsonParser.nextToken() != JsonToken.END_ARRAY){
    myLinkedHashMap  = mapper.readValue(jsonParser, LinkedHashMap.class);
}

变量myLinkedHashMap将包含JSON文件中对象的键/值对。

但问题是,JSON文件的'year'中,LinkedHashMap中也会得到一个整数。

相反,我想在LinkedHashMap中将Integer作为String

请帮助我在LinkedHashMap中获取String而不是Integer

注意:解决方案应该也适用于其他数据类型。

因此,如果JSON对象包含布尔值true,那么我的LinkedHashMap应该包含"true"


为什么在使用值的同时不调用toString呢?toString会返回一个String - Ryuzaki L
@Deadpool,这段代码耦合度很高,无法进行更改。 - Zeus
如果您能定义自定义类,那么您可以做到这一点。 - Ryuzaki L
2个回答

3
您可以使用TypeFactoryconstructMapType方法构建地图类型,以精确告知readValue方法所需的内容。以下是示例:
import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonToken;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.type.MapType;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import org.springframework.util.Assert;

import java.io.File;
import java.util.LinkedHashMap;

public class JsonMapApp {

    public static void main(String[] args) throws Exception {
        File jsonFile = new File("./resource/test.json").getAbsoluteFile();

        ObjectMapper mapper = new ObjectMapper();
        mapper.registerModule(new JavaTimeModule());
        mapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);

        JsonParser jsonParser = mapper.getFactory().createParser(jsonFile);
        jsonParser.nextToken();

        MapType mapType = mapper.getTypeFactory().constructMapType(LinkedHashMap.class, String.class, String.class);
        while (jsonParser.nextToken() != JsonToken.END_ARRAY) {
            LinkedHashMap<String, String> map = mapper.readValue(jsonParser, mapType);
            map.forEach((k, v) -> {
                Assert.isInstanceOf(String.class, v);
                System.out.println(k + " -> " + v + " (" + v.getClass().getName() + ")");
            });
        }
    }
}

上面的代码会输出:
name -> Fight Club (java.lang.String)
year -> 1999 (java.lang.String)

0

更改

Map<String, Object> myLinkedHashMap;

 Map<String, String> myLinkedHashMap;

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