我有一个类的一些字段,例如
public class Message {
public Enum Type {
TEXT,
PICTURE;
}
private Type type;
private String text;
private int id;
}
假设我有一个json,如下所示
[ { "id" : "1",
"data" : "hello",
"type" : "text",
},
{ "id" : "2",
"data" : "<someImageUrl>",
"type" : "picture",
},
]
我可以很容易地通过调用
来反序列化它Gson gson = new Gson();
ArrayList<Message> messages = gson.fromJson(jsonResult, new TypeToken<List<Message>>() {}.getType());
酷。不幸的是,Type字段仍然为空,因为json对象和枚举中定义的实例之间的大小写不同。我怎样才能改变gson的行为,使它将json类型对象解释为大写。
我想到的可能的解决方法:
- 将序号值分配给enum类型,以匹配json中给出的内容(即
TEXT("text")
)。 - 用分隔符"}"分割json结果,
- 将出现的- someenumtype -替换为- someenumtype -
比如
public enum Type {
TEXT("text"),
PICTURE("picture");
private final String value
private MessageType(String value) {
this.value = value;
}
public String getValue() {
return value
}
}
...
String[] jsonResultSplit = StringUtils.split(jsonResult, "},")
for (String jsonMessage : jsonResultSplit) {
for (MessageType messageType : MessageType.values()) {
if (jsonMessage.contains(""type:" : "" + messageType.getValue() + """)) {
jsonMessage.replace(
""type:" : "" + messageType.getValue() + """,
""type:" : ""
+ StringUtils.capitalize(messageType.getValue() + """));
}
}
}
jsonResult = StringUtils.join(jsonResultSplit);
Gson gson = new Gson();
ArrayList<Message> messages = gson.fromJson(jsonResult, new TypeToken<List<Message>>() {}.getType());
然而,这似乎有点粗糙,如果消息包含"}"或其他内容,字符串将被错误地分割。
最简单的方法是为Enum使用@SerializedName注释。
public Enum Type {
@SerializedName("text")
TEXT,
@SerializedName("picture")
PICTURE
}
@SerializedName
不仅可以用于大写,还可以用于更改枚举或变量的名称,例如
public enum Gender {
@SerializedName("boy")
MALE,
@SerializedName("girl")
FEMALE
}
参考也正如@Sotirios建议的那样,您需要注释text
以映射json键与您的变量。
@SerializedName("data")
private String text;
你现在可以使用以前的Gson来反序列化json了
Gson gson = new Gson();
ArrayList<Message> messages = gson.fromJson(jsonResult, new TypeToken<List<Message>>() {}.getType());
您必须注册自己的TypeAdapter
来进行转换
Gson gson = new GsonBuilder().registerTypeAdapter(Type.class,
new TypeAdapter<Type>() {
@Override
public void write(JsonWriter out, Type value)
throws IOException {
out.value(value.name().toLowerCase());
}
@Override
public Type read(JsonReader in) throws IOException {
return Type.valueOf(in.nextString().toUpperCase());
}
}).create();
注意,您还应该注释
private String text;
使用@SerializedName("data")
,因为它不匹配JSON名称。
"data" : "hello",