序列化接口列表GSON [英] Serializing List of Interfaces GSON
问题描述
如果我有以下类结构:
public interface Animal {
public void nothing();
}
公共类Cat实现Animal {
私有字符串名称;
public Cat(String name){
super();
this.name = name;
$ b $ public Cat(){}
@Override
public void nothing(){
// TODO自动生成的方法存根
};
}
public class Dog implements Animal {
private String name;
public Dog(String name){
super();
this.name = name;
$ b $ public Dog(){}
@Override
public void nothing(){
// TODO自动生成的方法存根
};
}
我可以这样做:
ArrayList< Animal> animals = new ArrayList< Animal>();
animals.add(new Cat(Betty));
animals.add(新狗(Fred));
System.out.println(gson.toJson(animals));
并获得此输出:
[{name:Betty},{name:Fred}]
然而,如果我把 animals
放入一个包含类中:
public class Container {
List< Animal> animals = new ArrayList< Animal>();
public void addAnimal(Animal a){
animals.add(a);
}
}
并致电:
Container container = new Container();
container.addAnimal(new Cat(betty));
System.out.println(gson.toJson(container));
我得到:
{animals:[{}]}
当列表本身是列表时,序列化接口列表列表
,但当列表包含在另一个类中时,GSON会有问题。
任何想法我做错了什么?
作为一个方面说明,我可以正确反序列化一个json字符串到正确的类型使用一个自定义的解串器。这是序列化,给我的问题。
谢谢 解决方案
这远非漂亮,但我现在使用的解决方案是使用
JsonObject jsonObject = gson.toJsonTree(container) .getAsJsonObject();
来构建一个JsonObject。然后我打电话:
jsonObject.remove(animals);
jsonObject.add(animals,gson.toJsonTree(container.getAnimals()));
和waa laa,对象的格式为正确。
奖励要点:我有一个嵌套容器的列表,所以我必须构造一个JsonArray,以便遍历我的容器并在每个容器上调用我的自定义toJson()。
故事的道德:使用
jsonObject.remove();添加接口列表。
jsonObject.add(propertyName,property);
使用JsonArray技巧和迭代容器列表(仅在列表中使用toJson()对孩子的容器不要求你特别的方法。)
绝对仍然在寻找更自然的解决方案。
快乐编码
I came across some weird behavior in GSON.
If I have the following class structure:
public interface Animal {
public void nothing();
}
public class Cat implements Animal {
private String name;
public Cat(String name) {
super();
this.name = name;
}
public Cat(){}
@Override
public void nothing() {
// TODO Auto-generated method stub
};
}
public class Dog implements Animal {
private String name;
public Dog(String name) {
super();
this.name = name;
}
public Dog(){}
@Override
public void nothing() {
// TODO Auto-generated method stub
};
}
I can do this:
ArrayList<Animal> animals = new ArrayList<Animal>();
animals.add(new Cat("Betty"));
animals.add(new Dog("Fred"));
System.out.println(gson.toJson(animals));
and get this output:
[{"name":"Betty"},{"name":"Fred"}]
However, if I put animals
into a containing class:
public class Container {
List<Animal> animals = new ArrayList<Animal>();
public void addAnimal(Animal a){
animals.add(a);
}
}
and call:
Container container = new Container();
container.addAnimal(new Cat("betty"));
System.out.println(gson.toJson(container));
I get:
{"animals":[{}]}
It looks like GSON can serialize a list of an interface List<Interface>
when that list is by itself, but when the list is contained in another class, GSON has problems.
Any idea what I'm doing wrong?
As a side note, I can correctly deserialize a json string into the correct type using a custom deserializer. It's the serializing that is giving me issues.
Thanks
It's far from pretty, but the solution I'm using for now is to use
JsonObject jsonObject = gson.toJsonTree(container).getAsJsonObject();
to build a JsonObject. Then I call:
jsonObject.remove("animals");
jsonObject.add("animals",gson.toJsonTree(container.getAnimals()));
and waa laa, the object in correct json form.
Bonus points: I had a list of nested containers, so I had to construct a JsonArray so that I could iterate over my containers and call my custom toJson() on each.
Moral of the story: Add Interface Lists using the
jsonObject.remove();
jsonObject.add(propertyName, property);
trick and iterate over a List of containers using a JsonArray (just using toJson() on the list doesn't call your special method on children containers).
Definitely still looking for a more natural solution.
Happy coding
这篇关于序列化接口列表GSON的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!