Gson自定义deseralizer对象中的一个变量 [英] Gson custom deseralizer for one variable in an object

查看:115
本文介绍了Gson自定义deseralizer对象中的一个变量的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的问题例子:



我们有一个Apple的对象类型。 Apple有一些成员变量:

 字符串appleName; //苹果名称
字符串appleBrand; //苹果品牌
列表< Seed>种子; //苹果种子列表

种子对象如下所示。

 字符串seedName; //种子名称
long seedSize; //种子的大小

现在,当我得到一个苹果对象时,一个苹果可能会超过一个种子,或者它可以有一个种子,或可能没有种子!



示例JSON苹果和一个种子:



< pre $ {
apple:{
apple_name:Jimmy,
apple_brand:Awesome Brand,
seeds:{seed_name:Loopy,seed_size:14}
}
}

示例带有两个种子的JSON苹果:

  {
apple: {
apple_name:Jimmy,
apple_brand:Awesome Brand,
seeds:[
{
seed_name:Loopy ,
seed_size:14
},
{
seed_name:Quake,
seed_size:26
}
]}
}

现在这个问题是第一个例子是种子的JSONObject,第二个例子是种子的JSONArray。现在我知道它不一致的JSON,修复它的最简单方法是修复JSON本身,但不幸的是我从其他人那里获得JSON,所以我无法修复它。解决此问题的最简单方法是什么?

解决方案

您需要为<$ c $注册一个自定义类型适配器c> Apple 类型。在类型适配器中,您将添加逻辑来确定您是否获得数组或单个对象。使用这些信息,你可以创建你的 Apple 对象。



除了下面的代码,修改你的Apple模型对象,这样种子字段不会自动分析。将变量声明更改为如下所示:

  private List< Seed> seeds_funkyName; 

以下是代码:

  GsonBuilder b = new GsonBuilder(); 
b.registerTypeAdapter(Apple.class,new JsonDeserializer< Apple>(){
@Override
public Apple反序列化(JsonElement arg0,类型arg1,
JsonDeserializationContext arg2)throws JsonParseException {
JsonObject appleObj = arg0.getAsJsonObject();
Gson g = new Gson();
//构造一个苹果(这不应该试图解析种子的东西
Apple a = g.fromJson(arg0,Apple.class);
List< Seed> seeds = null;
//检查我们是否得到一个列表或一个种子
if( appleObj.get(seeds)。isJsonArray()){
//如果它是一个列表,只需从JSON中解析
seeds = g.fromJson(appleObj.get(seeds),
new TypeToken< List< Seed>>(){
} .getType());
} else {
//解析单个种子
//并将其添加到列表
中Seed single = g.fromJson(appleObj.get(seeds),Seed.class);
seeds = new ArrayList< Seed>();
seeds.add(single);
}
//设置正确的种子列表
a.setSeeds(seeds);
返回a;
}
});

有关更多信息,请参阅 Gson指南


My probelm example:

We have an object type of Apple. Apple has some member variables:

String appleName; // The apples name
String appleBrand; // The apples brand
List<Seed> seeds; // A list of seeds the apple has

And the seed object looks as follows.

String seedName; // The seeds name
long seedSize; // The size of the seed

Now When I get an apple object, an apple could have more than one seed, or it could have one seed, or maybe no seeds!

Example JSON apple with one seed:

{
"apple" : {
   "apple_name" : "Jimmy", 
   "apple_brand" : "Awesome Brand" , 
   "seeds" : {"seed_name":"Loopy" , "seed_size":"14" }
  }
}

Example JSON apple with two seeds:

{
"apple" : {
   "apple_name" : "Jimmy" , 
   "apple_brand" : "Awesome Brand" , 
   "seeds" : [ 
      { 
         "seed_name" : "Loopy",
         "seed_size" : "14"
      },
      {
         "seed_name" : "Quake",
         "seed_size" : "26"
      } 
  ]}
}

Now the issue here is the first example is a JSONObject for seeds, the second example is a JSONArray for seeds. Now I know its inconsistent JSON and the easiest way to fix it would be fix the JSON itself, but unfortunately I'm getting the JSON from some one else, so I cant fix it. What would be the easiest way to fix this issue?

解决方案

You need to register a custom type adapter for the Apple type. In the type adapter, you will add logic to determine if you were given an array or a single object. Using that info, you can create your Apple object.

In adition to the below code, modify your Apple model object so that the seeds field isn't automatically parsed. Change the variable declaration to something like:

private List<Seed> seeds_funkyName;

Here is the code:

GsonBuilder b = new GsonBuilder();
b.registerTypeAdapter(Apple.class, new JsonDeserializer<Apple>() {
    @Override
    public Apple deserialize(JsonElement arg0, Type arg1,
        JsonDeserializationContext arg2) throws JsonParseException {
        JsonObject appleObj = arg0.getAsJsonObject();
        Gson g = new Gson();
        // Construct an apple (this shouldn't try to parse the seeds stuff
        Apple a = g.fromJson(arg0, Apple.class);
        List<Seed> seeds = null;
        // Check to see if we were given a list or a single seed
        if (appleObj.get("seeds").isJsonArray()) {
            // if it's a list, just parse that from the JSON
            seeds = g.fromJson(appleObj.get("seeds"),
                    new TypeToken<List<Seed>>() {
                    }.getType());
        } else {
            // otherwise, parse the single seed,
            // and add it to the list
            Seed single = g.fromJson(appleObj.get("seeds"), Seed.class);
            seeds = new ArrayList<Seed>();
            seeds.add(single);
        }
        // set the correct seed list
        a.setSeeds(seeds);
        return a;
    }
});

For some more info, see the Gson guide.

这篇关于Gson自定义deseralizer对象中的一个变量的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆