使用Gson反序列化有时是字符串,有时是对象

4
我需要将这种类型的JSON数据解析为Java对象:
{"id": 1, "blob": "example text"} 
{"id": 2, "blob": {"to": 1234, "from": 4321, "name": "My_Name"}}

我正在使用Gson,但不知道如何解决这个问题,“blob”有时是一个字符串,有时是一个对象。


我不太确定你的问题是什么。你是指我能否手动更改JSON的布局吗? - user1090614
你需要blob:“示例文本值”吗? - Prabhakaran Ramaswamy
是的,我需要让blob既可以是一个字符串的情况,也可以是一个对象的情况。 - user1090614
@user2864750 但这不是我的问题。我无法控制数据的生成方式或其结构 - 因此修复结构不是一个选择。 - user1090614
@user1090614,你可以创建一个自定义的TypeAdapter,然后在确定正确的类型后,再次在内部使用GSON的POJO映射(使用提供的Reader)。这种方法将导致统一作为包装类型(即所创建的TypeAdapter)。 - user2864740
显示剩余3条评论
3个回答

4
您的问题有一种解决方案是为您的类编写 TypeAdapter,但是如果您的情况只有像在您的示例中那样,您可以使用最通用的类让 Gson 为您完成工作,从而实现相同的结果。

我的意思如下代码所示。

package stackoverflow.questions.q19478087;

import com.google.gson.Gson;

public class Q19478087 {

    public class Test {
        public int id;
        public Object blob;
        @Override
        public String toString() {
            return "Test [id=" + id + ", blob=" + blob + "]";
        }


    }

    public static void main(String[] str){
        String json1 = "{\"id\": 1, \"blob\": \"example text\"}";
        String json2 = "{\"id\": 2, \"blob\": {\"to\": 1234, \"from\": 4321, \"name\": \"My_Name\"}}";

        Gson g = new Gson();
        Test test1 = g.fromJson(json1, Test.class);
        System.out.println("Test 1: "+ test1);

        Test test2 = g.fromJson(json2, Test.class);
        System.out.println("Test 2: "+ test2);
    }

}

这是我的执行结果:

Test 1: Test [id=1, blob=example text]
Test 2: Test [id=2, blob={to=1234.0, from=4321.0, name=My_Name}]

在第二种情况下,blob会被反序列化为一个LinkedTreeMap,因此您可以使用((Map)test2.blob).get("to")访问其元素;如果需要类型适配器解决方案,请告诉我。

我写过,该blob将被反序列化为LinkedTreeMap,因此您可以使用((Map) test2.blob).get("to")来访问其元素。也许它之前没有得到很好的突出,因为我忘记了代码格式。现在已经修复了。 - giampaolo

0

试试这个

你的POJO

class FromToName{
    String to;
    String from;
    String name;
    @Override
    public String toString() {
        return "FromToName [to=" + to + ", from=" + from + ", name=" + name
                + "]";
    }
}

您的转换代码

  String json ="{\"id\": 1, \"blob\": \"example text\"}"; 
  //String json = "{\"id\": 2, \"blob\": {\"to\": 1234, \"from\": 4321, \"name\": \"My_Name\"}}";
  Gson gson = new Gson();
  JsonElement element = gson.fromJson (json, JsonElement.class);
  JsonObject jsonObj = element.getAsJsonObject();
  JsonElement id = jsonObj.get("id");
  System.out.println(id);
  if(jsonObj.get("blob") instanceof  JsonPrimitive  ){
         JsonElement blob = jsonObj.get("blob");
         System.out.println(blob);
   }else{
          FromToName blob = gson.fromJson (jsonObj.get("blob"), FromToName.class);
          System.out.println(blob);
   }

如果你对此有任何疑问,请让我知道


0

把它作为JSON元素,然后使用isMethods()在运行时确定类型。

文档

        JsonParser jp = new JsonParser();
        JsonElement ele = jp.parse(jsonString).getAsJsonObject().get("blob");;

            if (ele.isJsonObject()) {
                  //do related stuff here
            } else if (ele.isJsonArray()) {
                  //do related stuff here
            }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接