Gson,如何反序列化数组或空字符串

dev*_*vha 5 java android json gson

我试图将这个json反序列化为对象数组:

[{
    "name": "item 1",
    "tags": ["tag1"]
},
{
    "name": "item 2",
    "tags": ["tag1","tag2"]
},
{
    "name": "item 3",
    "tags": []
},
{
    "name": "item 4",
    "tags": ""
}]
Run Code Online (Sandbox Code Playgroud)

我的java类看起来像这样:

public class MyObject
{
    @Expose
    private String name;

    @Expose
    private List<String> tags = new ArrayList<String>();
}
Run Code Online (Sandbox Code Playgroud)

问题是json的tags属性,它可以只是空字符串或数组.现在gson给了我错误:com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: Expected BEGIN_ARRAY but was STRING

我应该如何反序化这个json?

我对这个json没有任何控制权,它来自第三个pary api.

Ale*_* C. 8

我对这个json没有任何控制权,它来自第三个pary api.

如果您无法控制数据,那么最好的解决方案是在我看来创建一个自定义反序列化器:

class MyObjectDeserializer implements JsonDeserializer<MyObject> {
    @Override
    public MyObject deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
        JsonObject jObj = json.getAsJsonObject();
        JsonElement jElement = jObj.get("tags");
        List<String> tags = Collections.emptyList();
        if(jElement.isJsonArray()) {
            tags = context.deserialize(jElement.getAsJsonArray(), new TypeToken<List<String>>(){}.getType());
        }
        //assuming there is an appropriate constructor
        return new MyObject(jObj.getAsJsonPrimitive("name").getAsString(), tags);
    }
}
Run Code Online (Sandbox Code Playgroud)

它检查是否"tags"是一个它做了什么JsonArray.如果是这种情况,它会像往常一样对其进行反序列化,否则您不会触摸它,只需使用空列表创建对象即可.

一旦你编写了它,你需要在JSON解析器中注册它:

Gson gson = new GsonBuilder().registerTypeAdapter(MyObject.class, new MyObjectDeserializer()).create();
//here json is a String that contains your input
List<MyObject> myObjects = gson.fromJson(json, new TypeToken<List<MyObject>>(){}.getType());
Run Code Online (Sandbox Code Playgroud)

运行它,我得到输出:

MyObject{name='item 1', tags=[tag1]}
MyObject{name='item 2', tags=[tag1, tag2]}
MyObject{name='item 3', tags=[]}
MyObject{name='item 4', tags=[]}
Run Code Online (Sandbox Code Playgroud)


slo*_*ott -1

您正在混合数据类型。你不能同时拥有数组和字符串。改变

"tags": ""
Run Code Online (Sandbox Code Playgroud)

"tags": null
Run Code Online (Sandbox Code Playgroud)

现在就可以走了。