为了账号安全,请及时绑定邮箱和手机立即绑定

Gson处理对象或数组

/ 猿问

Gson处理对象或数组

潇湘沐 2019-11-14 15:15:28

我有以下课程


public class MyClass {

    private List<MyOtherClass> others;

}


public class MyOtherClass {

    private String name;

}

我有可能看起来像这样的JSON


{

  others: {

    name: "val"

  }

}

或这个


{

  others: [

    {

      name: "val"

    },

    {

      name: "val"

    }

  ]

}

我希望能够MyClass对这两种JSON格式使用相同的格式。有办法用Gson做到这一点吗?


查看完整描述

3 回答

?
动漫人物

我想出了一个答案。


private static class MyOtherClassTypeAdapter implements JsonDeserializer<List<MyOtherClass>> {

    public List<MyOtherClass> deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext ctx) {

        List<MyOtherClass> vals = new ArrayList<MyOtherClass>();

        if (json.isJsonArray()) {

            for (JsonElement e : json.getAsJsonArray()) {

                vals.add((MyOtherClass) ctx.deserialize(e, MyOtherClass.class));

            }

        } else if (json.isJsonObject()) {

            vals.add((MyOtherClass) ctx.deserialize(json, MyOtherClass.class));

        } else {

            throw new RuntimeException("Unexpected JSON type: " + json.getClass());

        }

        return vals;

    }

}

像这样实例化Gson对象


Type myOtherClassListType = new TypeToken<List<MyOtherClass>>() {}.getType();


Gson gson = new GsonBuilder()

        .registerTypeAdapter(myOtherClassListType, new MyOtherClassTypeAdapter())

        .create();

那TypeToken是一个com.google.gson.reflect.TypeToken。


您可以在此处阅读有关解决方案的信息:


https://sites.google.com/site/gson/gson-user-guide#TOC-Serializing-and-Deserializing-Gener


查看完整回答
反对 回复 2019-11-14
?
慕沐林林

谢谢您提供的三个杯子!


如果需要多个类型,则与泛型类型相同:


public class SingleElementToListDeserializer<T> implements JsonDeserializer<List<T>> {


private final Class<T> clazz;


public SingleElementToListDeserializer(Class<T> clazz) {

    this.clazz = clazz;

}


public List<T> deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {

    List<T> resultList = new ArrayList<>();

    if (json.isJsonArray()) {

        for (JsonElement e : json.getAsJsonArray()) {

            resultList.add(context.<T>deserialize(e, clazz));

        }

    } else if (json.isJsonObject()) {

        resultList.add(context.<T>deserialize(json, clazz));

    } else {

        throw new RuntimeException("Unexpected JSON type: " + json.getClass());

    }

    return resultList;

    }

}

并配置Gson:


Type myOtherClassListType = new TypeToken<List<MyOtherClass>>() {}.getType();

SingleElementToListDeserializer<MyOtherClass> adapter = new SingleElementToListDeserializer<>(MyOtherClass.class);

Gson gson = new GsonBuilder()

    .registerTypeAdapter(myOtherClassListType, adapter)

    .create();


查看完整回答
反对 回复 2019-11-14
?
波斯汪

建立三杯的答案,我有以下让JsonArray直接反序列化为数组的方法。


static public <T> T[] fromJsonAsArray(Gson gson, JsonElement json, Class<T> tClass, Class<T[]> tArrClass)

        throws JsonParseException {


    T[] arr;


    if(json.isJsonObject()){

        //noinspection unchecked

        arr = (T[]) Array.newInstance(tClass, 1);

        arr[0] = gson.fromJson(json, tClass);

    }else if(json.isJsonArray()){

        arr = gson.fromJson(json, tArrClass);

    }else{

        throw new RuntimeException("Unexpected JSON type: " + json.getClass());

    }


    return arr;

}

用法:


    String response = ".......";


    JsonParser p = new JsonParser();

    JsonElement json = p.parse(response);

    Gson gson = new Gson();

    MyQuote[] quotes = GsonUtils.fromJsonAsArray(gson, json, MyQuote.class, MyQuote[].class);


查看完整回答
反对 回复 2019-11-14
  • 3 回答
  • 0 关注
  • 42 浏览
我要回答
慕课专栏
更多

添加回答

回复

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信