web-dev-qa-db-ja.com

jacksonで使用される@JsonTypeInfoおよび@JsonSubTypesとは

For in jacksonを使用する@JsonTypeInfoおよび@JsonSubTypesアノテーションとは何ですか?

public class Lion extends Animal {

private String name;

@JsonCreator
public Lion(@JsonProperty("name") String name) {
    this.name = name;
}

public String getName() {
    return name;
}

public String getSound() {
    return "Roar";
}

public String getType() {
    return "carnivorous";
}

public boolean isEndangered() {
    return true;
}

@Override
public String toString() {
    return "Lion [name=" + name + ", getName()=" + getName() + ", getSound()=" + getSound() + ", getType()=" + getType() + ", isEndangered()="
            + isEndangered() + "]";
}

}

========================================

public class Elephant extends Animal {

@JsonProperty
private String name;

@JsonCreator
public Elephant(@JsonProperty("name") String name) {
    this.name = name;
}

public String getName() {
    return name;
}

public String getSound() {
    return "trumpet";
}

public String getType() {
    return "herbivorous";
}

public boolean isEndangered() {
    return false;
}

@Override
public String toString() {
    return "Elephant [name=" + name + ", getName()=" + getName() + ", getSound()=" + getSound() + ", getType()=" + getType()
            + ", isEndangered()=" + isEndangered() + "]";
}
}

=============================================

@JsonTypeInfo (use = JsonTypeInfo.Id.CLASS, include = As.PROPERTY, property = "classNameExtenral")
@JsonSubTypes ({@Type (value = Lion.class, name = "lion"), @Type (value = Elephant.class, name = "elephant")})

public abstract class Animal {

@JsonProperty ("name")
String name;
@JsonProperty ("sound")
String sound;
@JsonProperty ("type")
String type;
@JsonProperty ("endangered")
boolean endangered;
}

public static void main(String[] args){
    Lion lion = new Lion("Simba");
    Elephant elephant = new Elephant("Manny");
    List<Animal> animals = new ArrayList<>();
    animals.add(lion);
    animals.add(elephant);
}

私が理解しているのはシリアル化されているオブジェクトの具体的なタイプを実際のデータとともにさらに保存することです。

私には明らかではないは、デシリアライズ中の実際の利点/ゲインです。

Java文書。

17
Harshit

これらの注釈の目的は、デシリアライゼーションでpolymorphismをサポートすることです。実行されている実際のコードをデシリアライズすると、期待されるもののclassがわかります。たとえば、逆シリアル化されるフィールドのタイプ。しかし、そのクラスにサブクラス(つまり、サブタイプ)がある場合、ジェネリックJacksonデシリアライザーは、デシリアライズされる文字列が実際のクラスであるとどのように知るのでしょうか?具体的な型(クラスまたはそのサブクラスの1つ)のインスタンスを作成し、それを埋める必要があります。どの情報を作成するかを知ることができる唯一の方法は、そもそもシリアル化にその情報がwrittenである場合です。

この回答 には3つの方法があります-ユースケースに適した方法を選択してください。 @JsonTypeInfo + @JsonSubtypesはそれらの方法の1つです。コンパイル時に、問題のクラスに存在する可能性のあるすべてのサブタイプを知っている場合に最適です。

25
davidbak