我有以下POJO:
public interface Shape {
public double calcArea();
public double calcPerimeter();
}
public class Rectangle implement Shape {
// Various properties of a rectangle
}
public class Circle implements Shape {
// Various properties of a circle
}
public class ShapeHolder {
private List<Shape> shapes;
// other stuff
}
我没有问题让GSON将ShapeHolder
的实例序列化为JSON。但是当我尝试将该JSON的String反序列化为ShapeHolder
实例时,我收到错误:
String shapeHolderAsStr = getString();
ShapeHolder holder = gson.fromJson(shapeHodlderAsStr, ShapeHolder.class);
抛出:
Exception in thread "main" java.lang.RuntimeException: Unable to invoke no-args constructor for interface
net.myapp.Shape. Register an InstanceCreator with Gson for this type may fix this problem.
at com.google.gson.internal.ConstructorConstructor$8.construct(ConstructorConstructor.java:167)
at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:162)
... rest of stack trace ommitted for brevity
所以我看了here并开始实现我自己的ShapeInstanceCreator
:
public class ShapeInstanceCreator implements InstanceCreator<Shape> {
@Override
public Shape createInstance(Type type) {
// TODO: ???
return null;
}
}
但是现在我被卡住了:我只给了java.lang.reflect.Type
,但我真的需要一个java.lang.Object
所以我可以编写如下代码:
public class ShapeInstanceCreator implements InstanceCreator<Shape> {
@Override
public Shape createInstance(Type type) {
Object obj = convertTypeToObject(type);
if(obj instanceof Rectangle) {
Rectangle r = (Rectangle)obj;
return r;
} else {
Circle c = (Circle)obj;
return c;
}
return null;
}
}
我该怎么办?提前谢谢!
更新:
Per @ raffian的建议(他/她发布的链接),我实现了InterfaceAdapter
完全,就像链接中的那个(我没有改变任何东西)。现在我得到以下例外:
Exception in thread "main" com.google.gson.JsonParseException: no 'type' member found in what was expected to be an interface wrapper
at net.myapp.InterfaceAdapter.get(InterfaceAdapter.java:39)
at net.myapp.InterfaceAdapter.deserialize(InterfaceAdapter.java:23)
有什么想法吗?
答案 0 :(得分:6)
你看过this了吗?看起来像是一种很好的实现InstanceCreators的方式。
我也在使用Gson,但由于序列化问题而切换到FlexJSON。使用Flex,您不需要实例创建者,只需确保您的对象具有基于JavaBean规范的所有字段的getter / setter,您就可以了:
ShapeHolder sh = new ShapeHolder();
sh.addShape(new Rectangle());
sh.addShape(new Circle());
JSONSerializer ser = new JSONSerializer();
String json = ser.deepSerialize(sh);
JSONDeserializer<ShapeHolder> der = new JSONDeserializer<ShapeHolder>();
ShapeHolder sh2 = der.deserialize(json);
答案 1 :(得分:0)
注意FlexJSON正在添加类名作为json的一部分,如下面的序列化时间。
{
"HTTPStatus": "OK",
"class": "com.XXX.YYY.HTTPViewResponse",
"code": null,
"outputContext": {
"class": "com.XXX.YYY.ZZZ.OutputSuccessContext",
"eligible": true
}
}
所以JSON会有些麻烦;但是你不需要在GSON中写InstanceCreator
。