作者: @dusunboy
如需转载需在明显位置保留作者信息及原文链接
如果博客中有不恰当之处欢迎留言交流
http://www.jianshu.com/p/1d3853ac0321
个人博客:http://www.dusunboy.io
约定格式JSON串
// data 为 object 的情况
{"status":"1","message":"错误信息提示或数据描述","data":{}}
// data 为 array 的情况
{"status":"0","message":"错误信息提示或数据描述","data":[]}
在工作中会经常遇到这样的约定格式,怎么写个好的封装能自动识别data是对象还是数组
Gson泛型解析
gson是支持泛型解析,从上边的格式,都会想到写两个对应的方法来封装
// 处理 data 为对象的情况
public static <T> BaseJsonBean<T> fromJson2Object() {}
// 处理 data 为数组的情况
public static <T> BaseJsonBean<ArrayList<T>> fromJson2Array(){}
用到的BaseJsonBean
public class BaseJsonBean<T> {
private String status;
private String message;
private T data;
private ArrayList<T> dataList;
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public T getData() {
return data;
}
public void setData(T data) {
this.data = data;
}
public ArrayList<T> getDataList() {
return dataList;
}
public void setDataList(ArrayList<T> dataList) {
this.dataList = dataList;
}
}
问题
这样就有个问题,每次我们都需要提前知道这个data是对象还是数组,才选择对应的方法
能不能让代码来自己判断呢,当然是可以的,使用Gson自定义反序列化
Gson自定义反序列化
使用GsonBuilder注册类型适配器registerTypeAdapter() 反序列化
public BaseJsonBean deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
Gson gson = new Gson();
BaseJsonBean baseJsonBean = new BaseJsonBean();
JsonObject jsonObject = json.getAsJsonObject();
JsonElement jsonDataElement = jsonObject.get("data");
baseJsonBean.setStatus(jsonObject.get("status").getAsString());
baseJsonBean.setMessage(jsonObject.get("message").getAsString());
if (jsonDataElement.isJsonArray()) {
baseJsonBean.setData(null);
baseJsonBean.setDataList(fromJson2Array(gson, jsonDataElement, aClass));
} else {
baseJsonBean.setData(fromJson2Object(gson, jsonDataElement, aClass));
baseJsonBean.setDataList(null);
}
return baseJsonBean;
}
使用示例
Gson gson = new GsonBuilder().registerTypeAdapter(BaseJsonBean.class,
new BaseJsonBeanDeserializer<>(DemoBean.class)).create();
BaseJsonBean<DemoBean> baseJsonBean = gson.fromJson(json,
new TypeToken<BaseJsonBean<DemoBean>>() {}.getType());
//获取对象
baseJsonBean.getData();
//获取数组
baseJsonBean.getDataList();
最后不管是哪种json数据格式就用一种来解析
源码地址
项目中用到的泛型生成库 TypeBuilder