【问题标题】:Gson can't deserialize multiple type ListGson 无法反序列化多种类型的 List
【发布时间】:2017-03-29 15:56:39
【问题描述】:

我有一个在ArrayList 中保存其他对象的类:

class Program {
    @Expose
    private List<BaseData> dataList;
}

我还有其他课程:

class BaseData {
    @Expose
    String name;
}

class Data extends BaseData {
    @Expose
    String description;
}

class DataA extends Data{
    @Expose
    String a;
}

class DataB extends Data{
    @Expose
    String b;
}

当我想序列化它时:

Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation().create();
Log.d(TAG, gson.toJson(myProgram));

我只能看到BaseData 中的密钥。我的Program 对象中的列表也包含DataADataBData 对象。

我该如何解决这个问题?

更新:

所以我的程序是这样工作的:它会做一些事情并用数据填充Program 的列表。比我保存它:我使用GsonProgram 转换为json 字符串。我使用Shared Preferences。 当我再次打开应用程序时,它会加载以前保存的 json 字符串。我Log.d它,一切都很酷。

我想从那个 json 创建一个 Program 对象。

Gson gson = new Gson();
instance = gson.fromJson(savedJson, Program.class);

在我用Gson 再次对其进行序列化之后,发生了我上面写的事情。所以它似乎只从json创建BaseData对象。

【问题讨论】:

  • 我打赌你没有初始化Data.descriptionDataA.aDataB.b,它们都是null。它必须至少适用于 Gson 2.8.0。
  • 你输了一个比。它们不是空的,我已经检查过了。
  • 你能提供初始化代码和你正在使用的Gson版本吗? gson.toJson(new Program(asList(new DataA("foo", "bar", "baz"), new DataB("foo", "bar", "baz")))) 生成以下 JSON:{"dataList":[{"a":"baz","description":"bar","name":"foo"},{"b":"baz","description":"bar","name":"foo"}]}
  • 另外,尝试将serializeNulls() 添加到GsonBuilder 实例,以确保您的结果JSON 真正发生了什么。
  • 我尝试添加 serializeNulls() 但没有任何变化

标签: java android serialization gson


【解决方案1】:

我找到了解决方案

顺便说一句。感觉有点“蛮力”的方法。

Gson gson = new Gson();
JSONObject progJsonObj = new JSONObject(json);
progJsonObj.clearDataList();
JSONArray dataList= reader.getJSONArray("dataList");
Program program = gson.fromJson(progJsonObj.toString());
for (int i = 0; i < dataList.length(); i++) {
    JSONObject blockData = blocksInProgram.getJSONObject(i);
    // Added new class variable of the base class
    String type = blockData.getString("dataType");
    if (type.equals("data_a")) {
        DataA d = gson.fromJson(blockData.toString(), DataA.class);
        program.addData(d);
    } else if (type.equals("data_b")){
        DataB d = gson.fromJson(blockData.toString(), DataB.class);
        program.addData(d);
    }
}

【讨论】:

  • 你正在解决一个微不足道的反序列化问题,Gson 有一个额外的用于完全相同的目的:看看github.com/google/gson/blob/master/extras/src/main/java/com/…——查看 javadocs 如何为你解析数据类型。另外,除此之外,请注意JSONObjectJSONArray 来自org.json,在其他情况下可能不适用于Gson(您可能会与Gson 提供的JsonObjectJsonArray 混淆)。
  • @LyubomyrShaydariv 谢谢!我找到了那堂课,但为时已晚...再次感谢您的帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多