Как разобрать массив JSON с помощью Gson
Я хочу разобрать массивы JSON и использовать gson. Во-первых, я могу регистрировать вывод JSON, сервер четко отвечает клиенту.
вот мой вывод JSON:
[
{
id : '1',
title: 'sample title',
....
},
{
id : '2',
title: 'sample title',
....
},
...
]
я попробовал эту структуру для разбора. Класс, который зависит от одного array и ArrayList для всех JSONArray.
public class PostEntity {
private ArrayList<Post> postList = new ArrayList<Post>();
public List<Post> getPostList() {
return postList;
}
public void setPostList(List<Post> postList) {
this.postList = (ArrayList<Post>)postList;
}
}
Почта:
public class Post {
private String id;
private String title;
/* getters & setters */
}
когда я пытаюсь использовать gson без ошибок, без предупреждения и без журнала:
GsonBuilder gsonb = new GsonBuilder();
Gson gson = gsonb.create();
PostEntity postEnt;
JSONObject jsonObj = new JSONObject(jsonOutput);
postEnt = gson.fromJson(jsonObj.toString(), PostEntity.class);
Log.d("postLog", postEnt.getPostList().get(0).getId());
что случилось, как я могу решить?
5 ответов:
вы можете парсить
JSONArrayсразу, не нужно обернуть вашPostклассPostEntityеще раз и не нужны новыеJSONObject().toString()либо:Gson gson = new Gson(); String jsonOutput = "Your JSON String"; Type listType = new TypeToken<List<Post>>(){}.getType(); List<Post> posts = gson.fromJson(jsonOutput, listType);надеюсь, что это поможет.
Я искал способ разбора массивов объектов в более общем виде; вот мой вклад:
CollectionDeserializer.java:import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; import com.google.gson.Gson; import com.google.gson.JsonArray; import com.google.gson.JsonDeserializationContext; import com.google.gson.JsonDeserializer; import com.google.gson.JsonElement; import com.google.gson.JsonParseException; public class CollectionDeserializer implements JsonDeserializer<Collection<?>> { @Override public Collection<?> deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException { Type realType = ((ParameterizedType)typeOfT).getActualTypeArguments()[0]; return parseAsArrayList(json, realType); } /** * @param serializedData * @param type * @return */ @SuppressWarnings("unchecked") public <T> ArrayList<T> parseAsArrayList(JsonElement json, T type) { ArrayList<T> newArray = new ArrayList<T>(); Gson gson = new Gson(); JsonArray array= json.getAsJsonArray(); Iterator<JsonElement> iterator = array.iterator(); while(iterator.hasNext()){ JsonElement json2 = (JsonElement)iterator.next(); T object = (T) gson.fromJson(json2, (Class<?>)type); newArray.add(object); } return newArray; } }
JSONParsingTest.java:public class JSONParsingTest { List<World> worlds; @Test public void grantThatDeserializerWorksAndParseObjectArrays(){ String worldAsString = "{\"worlds\": [" + "{\"name\":\"name1\",\"id\":1}," + "{\"name\":\"name2\",\"id\":2}," + "{\"name\":\"name3\",\"id\":3}" + "]}"; GsonBuilder builder = new GsonBuilder(); builder.registerTypeAdapter(Collection.class, new CollectionDeserializer()); Gson gson = builder.create(); Object decoded = gson.fromJson((String)worldAsString, JSONParsingTest.class); assertNotNull(decoded); assertTrue(JSONParsingTest.class.isInstance(decoded)); JSONParsingTest decodedObject = (JSONParsingTest)decoded; assertEquals(3, decodedObject.worlds.size()); assertEquals((Long)2L, decodedObject.worlds.get(1).getId()); } }
World.java:public class World { private String name; private Long id; public void setName(String name) { this.name = name; } public String getName() { return name; } public Long getId() { return id; } public void setId(Long id) { this.id = id; } }
Type listType = new TypeToken<List<Post>>() {}.getType(); List<Post> posts = new Gson().fromJson(jsonOutput.toString(), listType);
некоторые из ответов этого сообщения действительны, но с помощью TypeToken библиотека Gson генерирует объекты дерева с нереальными типами для вашего приложения.
чтобы получить его, я должен был прочитать массив и преобразовать один за другим объекты внутри массива. Конечно этот метод не самый быстрый и я не рекомендую его использовать, если у вас массив слишком большой, но он сработал для меня.
необходимо включить в проект библиотеку Json. Если вы развиваетесь дальше Android, он входит:
/** * Convert JSON string to a list of objects * @param sJson String sJson to be converted * @param tClass Class * @return List<T> list of objects generated or null if there was an error */ public static <T> List<T> convertFromJsonArray(String sJson, Class<T> tClass){ try{ Gson gson = new Gson(); List<T> listObjects = new ArrayList<>(); //read each object of array with Json library JSONArray jsonArray = new JSONArray(sJson); for(int i=0; i<jsonArray.length(); i++){ //get the object JSONObject jsonObject = jsonArray.getJSONObject(i); //get string of object from Json library to convert it to real object with Gson library listObjects.add(gson.fromJson(jsonObject.toString(), tClass)); } //return list with all generated objects return listObjects; }catch(Exception e){ e.printStackTrace(); } //error: return null return null; }
вы можете получить значение списка без использования тип "объект".
EvalClassName[] evalClassName; ArrayList<EvalClassName> list; evalClassName= new Gson().fromJson(JSONArrayValue.toString(),EvalClassName[].class); list = new ArrayList<>(Arrays.asList(evalClassName));я испытывал его и он работает.
Comments