Kotlin中GSON解析报错:Expected BEGIN_OBJECT but was BEGIN_ARRAY
解决Gson解析JSON数组到自定义对象的异常问题
错误原因
你遇到的com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was BEGIN_ARRAY异常,核心是数据结构不匹配:
- API返回的是JSON数组(格式为
["/title/tt1649418/", "/title/tt10954984/"]) - 你定义的
PopularMovies是对象类型(对应JSON的{"popularMovies": [...]}结构)
Gson尝试将数组解析为对象,自然触发语法错误。
三种解决方案
方案一:直接解析为字符串列表(最简洁)
既然API返回的就是字符串数组,跳过自定义对象包装,直接解析成List<String>:
val gson = Gson() val movieIds: List<String> = gson.fromJson( jsonString, object : TypeToken<List<String>>() {}.type )
方案二:手动包装为自定义对象
如果必须使用PopularMovies类,先解析数组再手动构造对象:
val gson = Gson() // 先解析成字符串列表 val movieIdsList: List<String> = gson.fromJson( jsonString, object : TypeToken<List<String>>() {}.type ) // 构造自定义对象 val popularMovies = PopularMovies(ArrayList(movieIdsList))
方案三:自定义TypeAdapter自动适配
适合需要反复解析该结构的场景,编写TypeAdapter让Gson自动完成数组到对象的转换:
class PopularMoviesAdapter : TypeAdapter<PopularMovies>() { override fun write(out: JsonWriter, value: PopularMovies) { Gson().toJson(value.popularMovies, out) } override fun read(`in`: JsonReader): PopularMovies { val movieIds = Gson().fromJson<List<String>>( `in`, object : TypeToken<List<String>>() {}.type ) return PopularMovies(ArrayList(movieIds)) } }
使用时注册Adapter:
val gson = GsonBuilder() .registerTypeAdapter(PopularMovies::class.java, PopularMoviesAdapter()) .create() val popularMovies: PopularMovies = gson.fromJson(jsonString, PopularMovies::class.java)
推荐方案
优先选择方案一,完全贴合API返回结构,代码简洁且避免不必要的对象包装。
内容的提问来源于stack exchange,提问作者Vinicius Neves
相关产品推荐
相关产品推荐

