gpt4 book ai didi

java - 在 Java 中使用 Jackson 进行 map 反序列化

转载 作者:行者123 更新时间:2023-11-30 08:59:26 25 4
gpt4 key购买 nike

我有以下类(class)

public class BetWrapper {

private String description;
private Calendar startTime;
private HashMap<String, SimpleEntry<Integer, Double>> map;


public BetWrapper() {
map = new HashMap<>();
}

public Calendar getStartTime() {
return startTime;
}

public void setStartTime(Calendar startTime) {
this.startTime = startTime;
}

public String getDescription() {
return description;
}

public void setDescription(String description) {
this.description = description;
}

public HashMap<String, SimpleEntry<Integer, Double>> getMap() {
return map;
}

public void setMap(HashMap<String, SimpleEntry<Integer, Double>> map) {
this.map = map;
}

}

我正在使用 JSONUtil 类

public class JSONUtil {

private JSONUtil() {}

public static <T> T fromJSON(String content, Class<T> clazz) throws TechnicalException {
try {
return new ObjectMapper().readValue(content, clazz);
} catch (IOException e) {
throw new TechnicalException(e);
}
}

public static String toJSON(Object obj) throws TechnicalException {
try {
return new ObjectMapper().writeValueAsString(obj);
} catch (JsonProcessingException ex) {
throw new TechnicalException(ex);
}
}

}

我想将 JSON 反序列化为 BetWrapper 对象。但是下面的代码会产生一些异常。

BetWrapper betWrapper = new BetWrapper();
betWrapper.setDescription("Stoke City - Arsenal");
betWrapper.setStartTime(Calendar.getInstance());
HashMap<String, AbstractMap.SimpleEntry<Integer, Double>> map = new HashMap<>();
map.put("home_team", new AbstractMap.SimpleEntry<>(1, 2.85));
betWrapper.setMap(map);
String json = JSONUtil.toJSON(betWrapper);
JSONUtil.fromJSON(json, BetWrapper.class);

异常(exception)情况是:

Caused by: com.fasterxml.jackson.databind.JsonMappingException: No suitable constructor found for type [simple type, class java.util.AbstractMap$SimpleEntry<java.lang.Integer,java.lang.Double>]: can not instantiate from JSON object (need to add/enable type information?)
at [Source: {"description":"Stoke City - Arsenal","startTime":1417648132139,"map":{"home_team":"key":1,"value":2.85}}}; line: 1, column: 85] (through reference chain: by.bsu.kolodyuk.bettingapp.model.entity.BetWrapper["map"])

如何正确反序列化?看起来问题在于应该以某种方式为 Jackson 指定 SimpleEntry 中的 K、V 类型。

有什么想法吗?

最佳答案

SimpleEntry 类型具有以下构造函数

public SimpleEntry(K key, V value) {
this.key = key;
this.value = value;
}

默认情况下,Jackson 需要一个无参数的构造函数。如果这样的构造函数不存在,它会寻找带有 @JsonProperty 注释的构造函数。 (我可能会倒过来,但永远不要那样编码。)由于您使用的是 JDK 类型,它显然不会有这些注释。

您可以使用 Mixins。 Jackson 使用这些作为模板来反序列化您的目标类型。

abstract class Mixin<K, V> {
public Mixin(@JsonProperty("key") K key, @JsonProperty("value") V value) {}
}
...
public static <T> T fromJSON(String content, Class<T> clazz) throws Exception {
ObjectMapper mapper = new ObjectMapper();
mapper.addMixInAnnotations(SimpleEntry.class, Mixin.class);
return mapper.readValue(content, clazz);
}

Jackson 将使用元类型Mixin,反序列化为SimpleEntry 对象。

(请注意,Mixin 的类型参数和构造函数参数类型并不重要。重要的是有两个构造函数参数并且构造函数参数被注释。)

关于java - 在 Java 中使用 Jackson 进行 map 反序列化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27283479/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com