我有一个包含 T 类型字段的泛型类,Gson 将此字段序列化为空对象。我在下面添加了代码来演示该问题。读回 JSON 似乎没问题(只要您提供正确的类型标记)。
import java.lang.reflect.Type;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
public class GsonIssue {
static class AbstractThing {
private String fieldA = "valueA";
public String getFieldA() {
return fieldA;
}
public void setFieldA(String fieldA) {
this.fieldA = fieldA;
}
@Override
public String toString() {
return "AbstractThing [fieldA=" + fieldA + "]";
}
}
static class Thing extends AbstractThing {
private String fieldB = "valueB";
@Override
public String toString() {
return "Thing [fieldB=" + fieldB + ", fieldA=" + getFieldA() + "]";
}
}
static class Wrapper<T extends AbstractThing> {
private T abstractThing;
private String standardField = "standard value";
public Wrapper(T abstractThing) {
this.abstractThing = abstractThing;
}
@Override
public String toString() {
return "Wrapper [abstractThing=" + abstractThing + ", standardField=" + standardField + "]";
}
}
public static void main(String[] args) {
Wrapper<Thing> wrapper = new Wrapper<Thing>(new Thing());
Gson gson = new Gson();
String json = gson.toJson(wrapper);
System.out.println(json);
// prints : {"abstractThing":{},"standardField":"standard value"}
// so standardField is correctly serialized but not abstractThing.
// but if we manually construct the expected json string, and parse it back, we get the expected object structure
json = "{\"standardField\": \"some text\", " +
"\"abstractThing\":{\"fieldB\" : \"arb value\", \"fieldA\" : \"another arb value\"}}";
Type type = new TypeToken<Wrapper<Thing>>() {}.getType();
Object fromJson = gson.fromJson(json, type);
System.out.println(fromJson);
// prints : Wrapper [abstractThing=Thing [fieldB=arb value, fieldA=another arb value], standardField=some text]
// which is as expected
}
}
来自他们的文档:
当您调用 toJson(obj) 时,Gson 会调用 obj.getClass() 来获取要序列化的字段的信息。同样,您通常可以在 fromJson(json, MyClass.class) 方法中传递 MyClass.class 对象。如果对象是非泛型类型,则此方法可以正常工作。但是,如果对象是泛型类型,则泛型类型信息会因为 Java 类型擦除而丢失
您可以通过为泛型类型指定正确的参数化类型来解决此问题。您可以使用 TypeToken 类来完成此操作。
他们给出了以下示例List<T>
:
Type listType = new TypeToken<List<String>>() {}.getType();
gson.toJson(myStrings, listType);
所以对于你的代码,你需要......
Type myType = new TypeToken<Wrapper<Thing>>() {}.getType();
String json = gson.toJson(wrapper, myType);
https://sites.google.com/site/gson/gson-user-guide#TOC-Serializing-and-Deserializing-Gener https://sites.google.com/site/gson/gson-user-guide#TOC-Serializing-and-Deserializing-Gener
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)