Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/393.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何使用GSON反序列化不同对象的数组_Java_Json_Gson - Fatal编程技术网

Java 如何使用GSON反序列化不同对象的数组

Java 如何使用GSON反序列化不同对象的数组,java,json,gson,Java,Json,Gson,我收到这样的JSON [ { "albums" : [ {"id":"0", "name":"name"}, {"id":"1", "name":"name"} ], "name":"name" }, { "tracks" : [ {"id":"0", "name":"name", "duration":"3:30"}, {"id":"1", "name":"name", "duration":"2:40

我收到这样的JSON

[
  {
    "albums" : [
      {"id":"0", "name":"name"},
      {"id":"1", "name":"name"}
    ],
    "name":"name"
  },
  {
    "tracks" : [
      {"id":"0", "name":"name", "duration":"3:30"},
      {"id":"1", "name":"name", "duration":"2:40"}
    ],
    "name":"name"
  },
  {
    "playlists" : [
      {"id":"0", "name":"name", "tracksCount":"3"},
      {"id":"1", "name":"name", "tracksCount":"40"}
    ],
    "name":"name"
  }
]
当然,我实现了包含所有字段和类的类Track、Album和Playlist

Tracks {
  String name;
  List<Track> tracks;
}
Albums {
  String name;
  List<Album> albums;
}
Playlists {
  String name;
  List<Playlist> playlists;
}
JsonResponse在哪里

class JsonResponse {
  Albums albums;
  Tracks tracks;
  Playlists playlists;
}
但我得到了一个错误:

11-20 19:24:55.210:E/AndroidRuntime(5432):致命异常:main 11-20 19:24:55.210:E/AndroidRuntime(5432): com.google.gson.JsonSyntaxException:java.lang.IllegalStateException: 应为BEGIN_对象,但在第1行第13列11-20处为BEGIN_数组 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.ReflectTypeAdapterFactory$Adapter.read(ReflectTypeAdapterFactory.java:176) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.ReflectTypeAdapterFactory$1.read(reflectTypeAdapterFactory.java:93) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.ReflectTypeAdapterFactory$Adapter.read(ReflectTypeAdapterFactory.java:172) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.TypeAdapterRuntimeTypeWrapper.read(TypeAdapterRuntimeTypeWrapper.java:40) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.ArrayTypeAdapter.read(ArrayTypeAdapter.java:72) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 fromJson(gson.java:803)11-20 19:24:55.210: E/AndroidRuntime(5432):在 fromJson(gson.java:768)11-20 19:24:55.210: E/AndroidRuntime(5432):在 fromJson(gson.java:717)11-20 19:24:55.210: E/AndroidRuntime(5432):在 fromJson(gson.java:689)11-20 19:24:55.210: 11-20 19:24:55.210:E/AndroidRuntime(5432):在 android.os.ResultReceiver$MyRunnable.run(ResultReceiver.java:43)11-20 19:24:55.210:E/AndroidRuntime(5432):在 android.os.Handler.handleCallback(Handler.java:587)11-20 19:24:55.210:E/AndroidRuntime(5432):在 android.os.Handler.dispatchMessage(Handler.java:92)11-20 19:24:55.210:E/AndroidRuntime(5432):在 android.os.Looper.loop(Looper.java:130)11-20 19:24:55.210: E/AndroidRuntime(5432):在 android.app.ActivityThread.main(ActivityThread.java:3687)11-20 19:24:55.210:E/AndroidRuntime(5432):在 java.lang.reflect.Method.Invokenactive(本机方法)11-20 19:24:55.210:E/AndroidRuntime(5432):在 java.lang.reflect.Method.invoke(Method.java:507)11-20 19:24:55.210: E/AndroidRuntime(5432):在 com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:867) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.android.internal.os.ZygoteInit.main(ZygoteInit.java:625)11-20 19:24:55.210:E/AndroidRuntime(5432):在 dalvik.system.Nativestar.main(本机方法)11-20 19:24:55.210: E/AndroidRuntime(5432):由以下原因引起:java.lang.IllegalStateException: 应为BEGIN_对象,但在第1行第13列11-20处为BEGIN_数组 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.stream.JsonReader.beginObject(JsonReader.java:374) 11-20 19:24:55.210:E/AndroidRuntime(5432):在 com.google.gson.internal.bind.ReflectTypeAdapterFactory$Adapter.read(ReflectTypeAdapterFactory.java:165) 11-20 19:24:55.210:E/AndroidRuntime(5432):。。。还有21个

注意:json响应中的某些项目可能会丢失。比如说

[
  {
    "albums" : [
      {"id":"0", "name":"name"},
      {"id":"1", "name":"name"}
    ],
    "name":"name"
  }
 ]
那么问题是什么?我如何反序列化这个JSON


顺便说一句,我不能更改JSON。因此,我需要一个代码来解析它。

您发布的JSON没有显示JSONResponse对象数组,而是包含Albums、Tracks和Playlists类型的JSON对象。如果换成这样,情况会有所不同:

[
  {
     {
       "albums" : [
         {"id":"0", "name":"name"},
         {"id":"1", "name":"name"}
       ],
       "name":"name"
     },
     {
       "tracks" : [
         {"id":"0", "name":"name", "duration":"3:30"},
         {"id":"1", "name":"name", "duration":"2:40"}
       ],
       "name":"name"
     },
     {
       "playlists" : [
         {"id":"0", "name":"name", "tracksCount":"3"},
         {"id":"1", "name":"name", "tracksCount":"40"}
       ],
       "name":"name"
     }
   }
]
另外,如果您的对象过于复杂,请记住,在调用GSONBuilder对象上的create()之前,始终可以实现自己的JSONDeserializer类并在GSONBuilder对象上注册它。

这样做吗

[
  {
    "albums" : [
      {"id":"0", "name":"name"},
      {"id":"1", "name":"name"}
    ],
    "name":"name"
  },
  {
    "tracks" : [
      {"id":"0", "name":"name", "duration":"3:30"},
      {"id":"1", "name":"name", "duration":"2:40"}
    ],
    "name":"name"
  },
  {
    "playlists" : [
      {"id":"0", "name":"name", "tracksCount":"3"},
      {"id":"1", "name":"name", "tracksCount":"40"}
    ],
    "name":"name"
  }
]
你的数据

    String json = "[{\"albums\":[{\"id\":\"0\",\"name\":\"name\"},{\"id\":\"1\",\"name\":\"name\"}],\"name\":\"name\"},{\"tracks\":[{\"id\":\"0\",\"name\":\"name\",\"duration\":\"3:30\"},{\"id\":\"1\",\"name\":\"name\",\"duration\":\"2:40\"}],\"name\":\"name\"},{\"playlists\":[{\"id\":\"0\",\"name\":\"name\",\"tracksCount\":\"3\"},{\"id\":\"1\",\"name\":\"name\",\"tracksCount\":\"40\"}],\"name\":\"name\"}]";
你的波乔

class JsonResponse {
      ArrayList<Album> albums;
      ArrayList<Track> tracks;
      ArrayList<Playlist> playlists;
      String name;
    @Override
    public String toString() {
        return "JsonResponse [albums=" + albums + ", tracks=" + tracks
                + ", playlists=" + playlists + ", name=" + name + "]";
    }     
}



class Track{
    int id;
    String name;
    String duration;
    @Override
    public String toString() {
        return "Track [id=" + id + ", name=" + name + ", duration=" + duration
                + "]";
    }    
}

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

class Playlist{ 
    int id;
    String name;
    int tracksCount;
    @Override
    public String toString() {
        return "Playlist [id=" + id + ", name=" + name + ", tracksCount="
                + tracksCount + "]";
    }

}

实际上,您在JsonResponse类中犯了错误

它明确表示json格式是从数组开始的,在JsonResponse类中,您只需编写单个对象,而不是对象的集合。如果您仔细查看Gson异常 “
BEGIN\u对象,但它是BEGIN\u数组
”。这意味着Gason拥有唱片、曲目和播放列表的数组,而不是唱片、曲目和播放列表类的对象

只需在JsonResponse类中做一些更改,如下所示

private  List<Albums> albums;
private  List<Tracks> tracks;
private  List<Playlists> playlists;
私人列表相册;
私有列表轨道;
私人列表播放列表;

谢谢大家的帮助!这是我的解决办法

public class JsonResponse {
    public static class Item {
        String name;
    }

    public static class Tracks extends Item {
        List<Track> tracks;
    }

    public static class Albums extends Item {
        List<Album> albums;
    }

    public static class Playlists extends Item {
        List<Playlist> playlists;
    }

    public static class JsonResponseDeserialize implements JsonDeserializer<List<? extends Item>> {
        Gson gson = new Gson();
        @Override
        public List<? extends Item> deserialize(JsonElement el, Type type, JsonDeserializationContext context) throws JsonParseException {
            List<Item> ls = new ArrayList<Item>();
            JsonArray jarr = el.getAsJsonArray();
            for (JsonElement e : jarr) {
                Item i;
                if (e.getAsJsonObject().get("tracks") != null){
                    i = gson.lsomJson(e, Tracks.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
                if (e.getAsJsonObject().get("albums") != null){
                    i = gson.lsomJson(e, Albums.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
                if (e.getAsJsonObject().get("playlists") != null){
                    i = gson.lsomJson(e, Playlists.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
            }
            return ls;
        }
    }

    private Tracks _tracks;
    private Albums _albums;
    private Playlists _playlists;
}
公共类JsonResponse{
公共静态类项{
字符串名;
}
公共静态类跟踪扩展项{
列出曲目;
}
公共静态类相册扩展项{
列出相册;
}
公共静态类播放列表扩展项{
列出播放列表;
}

公共静态类JsonResponseDeserialize实现JsonDeserializer最近我出于同样的目的使用了RuntimeTypeAdapterFactory,这是一个简单的解决方案。它是一个开放的Gson集成(额外)

查看此帖子以查看和激活示例 我将原始代码从github直接导入到我的项目中(因为该类不直接拥有maven依赖项):

代码


希望有助于

我无法更改JSON。因此我需要一个代码来解析它。我知道JSON结构不在您的控制之下,但您误解了您所拥有的:您没有JSONResponse对象数组,而是播放列表、曲目等的数组……所以,没问题,您只需要实现自己的反序列化程序;下面是一个示例我无法更改JSON。因此我需要一个代码来解析它。希望您有Album、Track&Playlist类,只需更改JsonResponse,您的方法是正确的,只是JsonResponse类中有一个小错误。JsonResponse类包含对象,但不包含列表/数组,因为列表/数组旁边有一个字符串字段“name”。
public class JsonResponse {
    public static class Item {
        String name;
    }

    public static class Tracks extends Item {
        List<Track> tracks;
    }

    public static class Albums extends Item {
        List<Album> albums;
    }

    public static class Playlists extends Item {
        List<Playlist> playlists;
    }

    public static class JsonResponseDeserialize implements JsonDeserializer<List<? extends Item>> {
        Gson gson = new Gson();
        @Override
        public List<? extends Item> deserialize(JsonElement el, Type type, JsonDeserializationContext context) throws JsonParseException {
            List<Item> ls = new ArrayList<Item>();
            JsonArray jarr = el.getAsJsonArray();
            for (JsonElement e : jarr) {
                Item i;
                if (e.getAsJsonObject().get("tracks") != null){
                    i = gson.lsomJson(e, Tracks.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
                if (e.getAsJsonObject().get("albums") != null){
                    i = gson.lsomJson(e, Albums.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
                if (e.getAsJsonObject().get("playlists") != null){
                    i = gson.lsomJson(e, Playlists.class);
                    if (i != null) {
                        ls.add(i);
                        continue;
                    }
                }
            }
            return ls;
        }
    }

    private Tracks _tracks;
    private Albums _albums;
    private Playlists _playlists;
}
private static List<? extends Item> getDatalsomJson(String jsonString) {
    Type type = new TypeToken<List<? extends JsonResponse.Item>>(){}.getType();
    GsonBuilder gb = new GsonBuilder();
    gb.registerTypeAdapter(type, new JsonResponse.JsonResponseDeserialize());
    Gson gson = gb.create();
    List<? extends Item> ls = gson.lsomJson(jsonString, type);
    return ls;
}