GSON вызывает исключение, если тип объекта отличается

#java #android #gson

#java #Android #gson

Вопрос:

Я использую следующий подход для анализа канала в объекты Java.

    val gsonBuilder = GsonBuilder()
        val gson = gsonBuilder.create()
        var homeModel: DataModel?=null

        try {
            homeModel = gson.fromJson(response, DataModel::class.java)
        }catch (ex:java.lang.Exception){
        }
  

Это отлично работает, если поток поступает в том же формате, но тип какого-либо объекта изменяет его попадание в блок исключений.

Например, канал некоторое время предоставляет «целые числа» вместо объекта в «данных»

 @SerializedName("data")
@Expose
private List<MoreData> data = null;
  

Я хочу знать, есть ли в GSON какая-либо возможность установить для определенных данных значение «null», если тип не совпадает.

Комментарии:

1. В kotlin это просто, но в Java, я думаю, необходимо использовать метод serializeNulls: Gson gson = new GsonBuilder().serializeNulls().create();

2. @ManuelMato : я добавил «.serializeNulls()», но все равно получаю «java.lang. Исключение IllegalStateException: ожидаемый BEGIN_OBJECT, но был СТРОКОЙ в строке 1, столбец 11339, путь $»

Ответ №1:

вам нужно изменить тип данных «data» на List<Object> для java или List<Any> для kotlin. возможно, вы избавитесь от исключения.

 @SerializedName("data")
@Expose
private List<Object> data = null;
  

но вам нужно будет приводить элементы к соответствующим типам во время использования.

Например:

 val item:Int = homeModel[i] as Int //as yourDesiredType
  

Однако, если вы хотите установить значение «data» null, когда тип данных отличается, вы можете попробовать:

 val model = DataModel()
val json = Gson().toJson(model)
homeModel = Gson().fromJson(json, DataModel::class.java)
try {
        if(!homeModel.data.isNullOrEmpty()){
            homeModel.data.first() as String //as yourDesiredType
        }
} 
catch (ex:java.lang.Exception){
    homeModel.data = null
}
  

Комментарии:

1. Спасибо, List<Object> кажется, лучше избежать сбоя, могу ли я узнать, какой тип данных существует в List<Object>, если это int, string или моя модель.

2. Я думаю, вы можете это сделать: if(!homeModel.data.IsNullOrEmpty()){ if(homeModel.data.first() — строка) {doSomething()} else {doAnotherThing()} }