我有一个外部Web服务,它返回的名称为json
,像这样;
[
{
"page": 1,
"pages": 1,
"per_page": "310",
"total": 304
},
[
{
"id": "ABW",
"iso2Code": "AW",
"name": "Aruba",
"region": {
"id": "LCN",
"iso2code": "ZJ",
"value": "Latin America & Caribbean "
},
"adminregion": {
"id": "",
"iso2code": "",
"value": ""
},
"incomeLevel": {
"id": "HIC",
"iso2code": "XD",
"value": "High income"
},
"lendingType": {
"id": "LNX",
"iso2code": "XX",
"value": "Not classified"
},
"capitalCity": "Oranjestad",
"longitude": "-70.0167",
"latitude": "12.5167"
},
{
"id": "AFG",
"iso2Code": "AF",
"name": "Afghanistan",
"region": {
"id": "SAS",
"iso2code": "8S",
"value": "South Asia"
},
"adminregion": {
"id": "SAS",
"iso2code": "8S",
"value": "South Asia"
},
"incomeLevel": {
"id": "LIC",
"iso2code": "XM",
"value": "Low income"
},
"lendingType": {
"id": "IDX",
"iso2code": "XI",
"value": "IDA"
},
"capitalCity": "Kabul",
"longitude": "69.1761",
"latitude": "34.5228"
}
]
]
我有 CountriesResponse 类:
public class CountriesResponse {
private ResponseDetails responseDetails;
private List<Country> countries;
ResponseDetails :
class ResponseDetails {
@SerializedName("page")
@Expose
private int page;
@SerializedName("pages")
@Expose
private int pages;
@SerializedName("per_page")
@Expose
private String perPage;
@SerializedName("total")
@Expose
private int total;
国家:
public class Country {
@SerializedName("name")
private String name;
@SerializedName("capitalCity")
private String capital;
和 ApiInterface
public interface ApiInterface {
//http://api.worldbank.org/v2/countries/all?per_page=310&format=json
@GET("countries/all")
Call<ArrayList<Country>> getCountries(@Query("per_page") int per_page, @Query("format") String format);
}
在CountriesResponse
类中,我假设我要用@SerializedName
注释属性。我如何解析json
,看看json
中的对象和数组没有名称。
答案 0 :(得分:0)
1)您的呼叫返回了错误的类型。它应该返回您持有typedef struct {
int type_identifier; // or uint8_t
int access_mode; // or uint8_t
union {
char string[32];
struct { uint32_t val; uint32_t min; uint32_t max; uint32_t initial; } t_uint32;
struct { double val; double min; double max; double initial; } t_double;
struct { float val; float min; float max; float initial; } t_float;
struct { char val; char min; char max; char initial; } t_char;
} u;
} valueType;
的顶级对象CountriesResponse
,因为您想获取所有json,以便可以解析出匿名元素。
2)在ResponseDetails
中,您有一个CountriesResponse
,因为没有匹配的名称,因此无法在List<Country>.
中使用序列化注释。必须手动将其反序列化。因此,在两个字段中都不要使用“ Country
”。
3)使用Gson添加自定义解串器,请参见此处:Retrofit: how to parse a JSON array that combines an array and an object?
您需要将反序列化代码中的顶级JSON元素解析为包含2个元素的数组:
@SerializedName
要清楚地看到结构,可以使用https://jsoneditoronline.org并将JSON放在此处。
您的反序列化器如下所示:
final JsonArray jsonArray = json.getAsJsonArray();
JsonObject rd = jsonArray get(0); //this is the ResponseDetails object
CountriesResponse cr = new CountriesResponse();
cr.setResponseDetails(rd);
JsonArray countries = jsonArray.get(1) //<-- this is your List<Country>
//now you must iterate list `countries`and create a new Country for each one then add it to the List<Country> in CountriesResponse
现在,您具有cr.getCountriesList()来显示数据。 JSONElements可能需要强制转换,但这实际上是要执行的操作。 Retrofit / POJO / JSON转换器不提供的一件事是匿名元素支持。
如果您需要将其保留在Room中,则还需要TypeConverter作为列表。