1 回答

TA貢獻1784條經驗 獲得超8個贊
我真的不知道在沒有手動或hacky的情況下使用gson執行此操作的方法。這太大了,無法作為評論發表,因此我將其留在這里作為答案,以幫助您解決問題。
首先,您會遇到堆棧溢出,因為您正在調用context.deserialize相同的參數,這些參數觸發gson調用相同的反序列化器,它將再次調用context.deserialize,依此類推,直到堆棧溢出。
序列化時你會遇到同樣的問題,因為你也只是在做context.serialize.
為避免這種情況,您需要避免gson遞歸調用序列化器/反序列化器的方法。這很容易通過創建另一個gson沒有適配器的實例來實現:
public class PetAdapter
implements JsonSerializer<Pet>, JsonDeserializer<Pet> {
private final Gson gson = new Gson();
@Override
public Pet deserialize(JsonElement jsonElement, Type typeOfT,
JsonDeserializationContext context) throws JsonParseException {
EntityType entityType = EntityType.valueOf(jsonElement.getAsJsonObject().get("entityType").getAsString());
switch (entityType) {
case IRON_GOLEM:
return gson.fromJson(jsonElement, EcoPet.class);
case WOLF:
return gson.fromJson(jsonElement, BoostPet.class);
case MAGMA_CUBE:
return gson.fromJson(jsonElement, CombatPet.class);
default:
throw new JsonParseException("Invalid PetType");
}
}
@Override
public JsonElement serialize(Pet src, Type typeOfSrc, JsonSerializationContext context) {
return gson.toJson(src);
}
}
這有效,但前提是您的Pet實現不依賴于其他自定義序列化器/反序列化器。所以你可以想象這很hacky。
另一種方法是手動反序列化。這意味著您必須通過 json 元素并讀取屬性,就像您正在閱讀entityType和手動構建您的對象一樣。
非常相似,我想(我沒有檢查這個),您可以首先context將每個寵物反序列化為一個Map對象,并讓每個寵物實現一個靜態方法,該方法從該地圖創建特定寵物的實例。就像是:
public class IronGolem extends Pet {
public static IronGolem from(Map<String, Object> deserializedPet) {
// here check the map for each thing you need
return new IronGolem(/*pass in every attribute*/);
}
}
希望這可以幫助。
添加回答
舉報