我正在使用gson来反序列化对象,我告诉gson接口类而不是我想要的对象的实现类。我注册了一个构造实现类实例的InstanceCreator
。
此测试演示了我遇到的问题:
public class UnexpectedGsonBehaviorTest {
public static interface Fruits {
List<String> getFruitList();
}
public static class FruitsImpl implements Fruits {
private List<String> fruitList;
public List<String> getFruitList() {
return fruitList;
}
public String toString() {
return "FruitsImpl{" + "fruitList=" + fruitList + '}';
}
}
@Test
public void testUseCustomFruitsInstanceCreator() {
Gson gson = new GsonBuilder()
.registerTypeAdapter(Fruits.class, new InstanceCreator<Fruits>(){
public Fruits createInstance(Type type) {
return new FruitsImpl();
}
}).create();
String fruitsJson = "{\"fruitList\": [\"apples\", \"pears\", \"bananas\"]}";
System.out.println("input: " + fruitsJson);
Fruits fruits = gson.fromJson(fruitsJson, Fruits.class);
System.out.println("output: " + fruits);
assertNotNull("expect non-null fruit list", fruits.getFruitList());
}
}
我希望反序列化FruitsImpl
对象的列表成员,但事实并非如此。输出是
input: {"fruitList": ["apples", "pears", "bananas"]}
output: FruitsImpl{fruitList=null}
并且断言失败。
如果我只使用默认的gson实例和gson.fromJson(fruitsJson, FruitsImpl.class)
,则列表字段会被正确反序列化。我使用gson是错误的,还是有其他问题?
答案 0 :(得分:0)
如果您调试它并在createInstance
内放置一个断点并进入gson代码,您应该会看到问题。
实例化后,gson尝试填充ReflectiveTypeAdapterFactory
中的所有绑定字段。在您的情况下,绑定字段映射为空。这是因为它无法检查您的接口是否有字段。
来自getBoundFields
ReflectiveTypeAdapterFactory
Map<String, BoundField> result = new LinkedHashMap<String, BoundField>();
if (raw.isInterface()) {
return result;
}
因此,如果你告诉gson反序列化的类型没有零参数构造函数供gson调用,那么实例创建者更合适。