我正在尝试浏览Programmer Bruce的教程,该教程应该允许多态JSON的反序列化。
完整列表可以在这里找到 Programmer Bruce教程(顺便说一句)
我已经完成了前五项工作,没有任何问题,但是我在最后一项中遇到了麻烦(示例6),这当然是我真正需要工作的部分。
编译时出现以下错误
ObjectMapper类型的方法readValue(JsonParser,Class)不适用于参数(ObjectNode,Class)
这是由代码块引起的
public Animal deserialize( JsonParser jp, DeserializationContext ctxt) throws IOException, JsonProcessingException { ObjectMapper mapper = (ObjectMapper) jp.getCodec(); ObjectNode root = (ObjectNode) mapper.readTree(jp); Class<? extends Animal> animalClass = null; Iterator<Entry<String, JsonNode>> elementsIterator = root.getFields(); while (elementsIterator.hasNext()) { Entry<String, JsonNode> element=elementsIterator.next(); String name = element.getKey(); if (registry.containsKey(name)) { animalClass = registry.get(name); break; } } if (animalClass == null) return null; return mapper.readValue(root, animalClass); } }
具体按行
返回mapper.readValue(root,animalClass);
之前有人遇到过这个问题吗?如果有,有解决方案吗?
任何人都可以给您的帮助,我将不胜感激。
如所承诺的,我将举一个如何使用注释对多态对象进行序列化/反序列化的示例,该示例基于Animal您正在阅读的教程中的类。
Animal
首先,在您的Animal类中使用子类的Json注释。
import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import com.fasterxml.jackson.annotation.JsonSubTypes; import com.fasterxml.jackson.annotation.JsonTypeInfo; @JsonIgnoreProperties(ignoreUnknown = true) @JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY) @JsonSubTypes({ @JsonSubTypes.Type(value = Dog.class, name = "Dog"), @JsonSubTypes.Type(value = Cat.class, name = "Cat") } ) public abstract class Animal { private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } }
然后是您的子类Dog和Cat。
Dog
Cat
public class Dog extends Animal { private String breed; public Dog() { } public Dog(String name, String breed) { setName(name); setBreed(breed); } public String getBreed() { return breed; } public void setBreed(String breed) { this.breed = breed; } } public class Cat extends Animal { public String getFavoriteToy() { return favoriteToy; } public Cat() {} public Cat(String name, String favoriteToy) { setName(name); setFavoriteToy(favoriteToy); } public void setFavoriteToy(String favoriteToy) { this.favoriteToy = favoriteToy; } private String favoriteToy; }
如您所见,Catand并没有什么特别的Dog,唯一了解它们的是abstractclass Animal,因此在反序列化时,您将定位到Animal并且ObjectMapper将返回实际实例,如以下测试所示:
abstract
ObjectMapper
public class Test { public static void main(String[] args) { ObjectMapper objectMapper = new ObjectMapper(); Animal myDog = new Dog("ruffus","english shepherd"); Animal myCat = new Cat("goya", "mice"); try { String dogJson = objectMapper.writeValueAsString(myDog); System.out.println(dogJson); Animal deserializedDog = objectMapper.readValue(dogJson, Animal.class); System.out.println("Deserialized dogJson Class: " + deserializedDog.getClass().getSimpleName()); String catJson = objectMapper.writeValueAsString(myCat); Animal deseriliazedCat = objectMapper.readValue(catJson, Animal.class); System.out.println("Deserialized catJson Class: " + deseriliazedCat.getClass().getSimpleName()); } catch (Exception e) { e.printStackTrace(); } } }
运行Test该类后的输出:
Test
{"@type":"Dog","name":"ruffus","breed":"english shepherd"}
Deserialized dogJson Class: Dog
{"@type":"Cat","name":"goya","favoriteToy":"mice"}
Deserialized catJson Class: Cat
希望这可以帮助,
何塞·路易斯