我遇到麻烦,这是一个我想用Jackson 2.3.2序列化/反序列化的课程。 序列化工作正常但不是反序列化。
我有如下例外:
找不到类型[simple type,class Series]的合适构造函数:无法从JSON对象实例化(需要添加/启用类型信息?)
最奇怪的是,如果我对构造函数进行注释,它就能完美运行!
public class Series {
private int init;
private String key;
private String color;
public Series(String key, String color, int init) {
this.key = key;
this.init = init;
this.color = color;
}
//Getters-Setters
}
我的单元测试:
public class SeriesMapperTest {
private String json = "{\"init\":1,\"key\":\"min\",\"color\":\"767\"}";
private ObjectMapper mapper = new ObjectMapper();
@Test
public void deserialize() {
try {
Series series = mapper.readValue(json, Series.class);
} catch (IOException e) {
Assert.fail(e.getMessage());
}
}
}
此异常是从Jackson lib deserializeFromObjectUsingNonDefault()
的{{1}}方法中抛出的。
有什么想法吗?
由于
答案 0 :(得分:5)
杰克逊没有强制要求类具有默认构造函数。您可以使用the @JsonCreator annotation注释现有构造函数,并使用@JsonProperty
注释将构造函数参数绑定到属性。
注意:如果您有单个构造函数,则甚至可以抑制@JsonCreator
。
这种方法具有创建真正不可变对象的优点,这对于各种good reasons来说是一件好事。
以下是一个例子:
public class JacksonImmutable {
public static class Series {
private final int init;
private final String key;
private final String color;
public Series(@JsonProperty("key") String key,
@JsonProperty("color") String color,
@JsonProperty("init") int init) {
this.key = key;
this.init = init;
this.color = color;
}
@Override
public String toString() {
return "Series{" +
"init=" + init +
", key='" + key + '\'' +
", color='" + color + '\'' +
'}';
}
}
public static void main(String[] args) throws IOException {
ObjectMapper mapper = new ObjectMapper();
String json = "{\"init\":1,\"key\":\"min\",\"color\":\"767\"}";
System.out.println(mapper.readValue(json, Series.class));
}
}
答案 1 :(得分:2)
您没有默认(即无参数)构造函数。
定义一个no-args构造函数:
public Series() {}
当您注释掉3-arg构造函数时它的工作原理是在java 中如果没有构造函数,则默认构造函数是隐式定义。
这会产生意想不到的效果,如果没有任何构造函数并且您定义了非默认构造函数,则(隐式)默认构造函数会消失!像你之前的许多人一样引导你,想知道发生了什么。