1概要

この記事では、https://github.com/FasterXML/jackson

を使用した

Javaマップのシリアライゼーションとデシリアライゼーションについて説明します。


Map <String、String>



Map <Object、String>、

および

Map <Object、Object>

をJSON形式の__Stringsとの間でシリアル化および逆シリアル化する方法を説明します。


2 Mavenの設定

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-databind</artifactId>
    <version>2.9.4</version>
</dependency>

あなたはジャクソンhttps://search.maven.org/classic/#search%7C1%7Cg%3A%22com.fasterxml.jackson.core%22%20AND%20a%3A%22jackson-databindの最新バージョンを入手することができます。 %22[ここ]


3直列化

直列化は、Javaオブジェクトをバイトストリームに変換します。このバイトストリームは、必要に応じて永続化または共有できます。 Javaの

Maps

は、キーの

Object

を値の

Object

にマップするコレクションで、多くの場合、直感的に理解しにくい直列化オブジェクトです。


3.1.

Map <String、String>

シリアライゼーション

簡単な例として、

Map <String、String>

を作成し、それをJSONにシリアル化します。

Map<String, String> map = new HashMap<>();
map.put("key", "value");

ObjectMapper mapper = new ObjectMapper();
String jsonResult = mapper.writerWithDefaultPrettyPrinter()
  .writeValueAsString(map);


ObjectMapper

は、Jacksonのシリアライゼーションマッパーです。これにより、

String



toString()

メソッドを使用して、

map

をシリアライズし、見栄えのよいJSON

String

として書き出すことができます。

{
  "key" : "value"
}


3.2.

Map <Object、String>

シリアライゼーション

いくつかの追加手順で、カスタムJavaクラスを含むマップをシリアル化できます。関連する

String

オブジェクトのペアを表す

MyPair

クラスを作成しましょう。

注:ゲッター/セッターはパブリックにする必要があります。ジャクソンがシリアライズ時にこのカスタムの

toString()

を確実に使用するように、

toString()



@ JsonValue

という注釈を付けます。

public class MyPair {

    private String first;
    private String second;

    @Override
    @JsonValue
    public String toString() {
        return first + " and " + second;
    }

   //standard getter, setters, equals, hashCode, constructors
}

では、Jacksonの

JsonSerializer

を拡張して、

MyPair

をシリアル化する方法をJacksonに伝えましょう。

public class MyPairSerializer extends JsonSerializer<MyPair> {

    private ObjectMapper mapper = new ObjectMapper();

    @Override
    public void serialize(MyPair value,
      JsonGenerator gen,
      SerializerProvider serializers)
      throws IOException, JsonProcessingException {

        StringWriter writer = new StringWriter();
        mapper.writeValue(writer, value);
        gen.writeFieldName(writer.toString());
    }
}


JsonSerializer

は、その名のとおり、

MyPair

`s

toString()

メソッドを使用して

MyPair

をJSONにシリアル化します。 Jacksonは、シリアル化の要件に合わせてhttps://fasterxml.github.io/jackson-databind/javadoc/2.3.0/com/fasterxml/jackson/databind/ser/std/package-summary.html[シリアル化クラス]を提供しています。


My <MyPair、String>



MyPairSerializer



@ JsonSerialize

アノテーションで適用します。

String:

をシリアル化する方法は既にわかっているので、

MyPair

をシリアル化する方法をJacksonに指示しただけであることに注意してください。

@JsonSerialize(keyUsing = MyPairSerializer.class)
Map<MyPair, String> map;

地図のシリアル化をテストしましょう。

map = new HashMap<>();
MyPair key = new MyPair("Abbott", "Costello");
map.put(key, "Comedy");

String jsonResult = mapper.writerWithDefaultPrettyPrinter()
  .writeValueAsString(map);

直列化されたJSON出力は次のとおりです。

{
  "Abbott and Costello" : "Comedy"
}


3.3.

Map <Object、Object>

シリアライゼーション

最も複雑なケースは

Map <Object、Object>

のシリアル化ですが、ほとんどの作業はすでに行われています。マップにはJacksonの

MapSerializer

を、マップのキーと値のタイプには前のセクションの

MyPairSerializer

を使用しましょう。

@JsonSerialize(keyUsing = MapSerializer.class)
Map<MyPair, MyPair> map;

@JsonSerialize(keyUsing = MyPairSerializer.class)
MyPair mapKey;

@JsonSerialize(keyUsing = MyPairSerializer.class)
MyPair mapValue;


Map <MyPair、MyPair>

をシリアル化してみましょう。

mapKey = new MyPair("Abbott", "Costello");
mapValue = new MyPair("Comedy", "1940s");
map.put(mapKey, mapValue);

String jsonResult = mapper.writerWithDefaultPrettyPrinter()
  .writeValueAsString(map);


MyPair

’s

toString()

メソッドを使用した、直列化されたJSON出力は、

{
  "Abbott and Costello" : "Comedy and 1940s"
}


4逆シリアル化

逆シリアル化は、バイトストリームをコード内で使用できるJavaオブジェクトに変換します。このセクションでは、JSON入力を異なるシグネチャの

Maps

に逆シリアル化します。


4.1.

Map <文字列、文字列>

逆シリアル化

簡単な例として、JSON形式の入力文字列を受け取り、それを

Map <String、String>

Javaコレクションに変換しましょう。

String jsonInput = "{\"key\": \"value\"}";
TypeReference<HashMap<String, String>> typeRef
  = new TypeReference<HashMap<String, String>>() {};
Map<String, String> map = mapper.readValue(jsonInput, typeRef);

シリアル化の場合と同じようにJacksonの

ObjectMapper

を使用します。入力を処理するには

readValue()

を使用します。また、私たちのすべての逆シリアル化の例で使用するJacksonの

TypeReference

の使用方法に注目してください。これがマップの

toString()

表現です。

{key=value}


4.2.

Map <Object、String>

デシリアライゼーション

それでは、入力JSONと宛先の

TypeReference



Map <MyPair、String>

に変更しましょう。

String jsonInput = "{\"Abbott and Costello\" : \"Comedy\"}";

TypeReference<HashMap<MyPair, String>> typeRef
  = new TypeReference<HashMap<MyPair, String>>() {};
Map<MyPair,String> map = mapper.readValue(jsonInput, typeRef);

両方の要素を持つ

String

を取り、それらを

MyPair

要素に解析する

MyPair

のコンストラクタを作成する必要があります。

public MyPair(String both) {
    String[]pairs = both.split("and");
    this.first = pairs[0].trim();
    this.second = pairs[1].trim();
}

また、

Map <MyPair、String>

オブジェクトの

toString()

は次のとおりです。

{Abbott and Costello=Comedy}


  • Map

    を含むJavaクラスにデシリアライズする場合のための別のオプションがあります – 私たちは多くのhttps://fasterxml.github.io/jackson-databind/javadoc/2.3.0のうちの1つである、Jacksonの

    KeyDeserializer

    クラス** を使用することができます。 Jacksonが提供する/com/fasterxml/jackson/databind/deser/package-summary.html[Deserialization]クラス。

    ClassWithAMap



    @ JsonCreator



    @ JsonProperty

    、および__ @ JsonDeserializeの注釈を付けます。

public class ClassWithAMap {

  @JsonProperty("map")
  @JsonDeserialize(keyUsing = MyPairDeserializer.class)
  private Map<MyPair, String> map;

  @JsonCreator
  public ClassWithAMap(Map<MyPair, String> map) {
    this.map = map;
  }

 //public getters/setters omitted
}


ClassWithAMap

に含まれる

Map <MyPair、String>

を逆シリアル化するようにJacksonに指示しているので、入力の

String

からマップのキー、

MyPair

オブジェクトを逆シリアル化する方法を記述するために

KeyDeserializer

を拡張する必要があります。

public class MyPairDeserializer extends KeyDeserializer {

  @Override
  public MyPair deserializeKey(
    String key,
    DeserializationContext ctxt) throws IOException,
    JsonProcessingException {

      return new MyPair(key);
    }
}


readValue

を使用して逆シリアル化をテストします。

String jsonInput = "{\"Abbott and Costello\":\"Comedy\"}";

ClassWithAMap classWithMap = mapper.readValue(jsonInput,
  ClassWithAMap.class);

繰り返しますが、

ClassWithAMapの

マップの

toString()

メソッドによって、期待される出力が得られます。

{Abbott and Costello=Comedy}


4.3.

Map <Object、Object>

逆シリアル化

最後に、入力JSONと宛先の

TypeReference



Map <MyPair、MyPair>

に変更しましょう。

String jsonInput = "{\"Abbott and Costello\" : \"Comedy and 1940s\"}";
TypeReference<HashMap<MyPair, MyPair>> typeRef
  = new TypeReference<HashMap<MyPair, MyPair>>() {};
Map<MyPair,MyPair> map = mapper.readValue(jsonInput, typeRef);

また、

Map <MyPair、MyPair>

オブジェクトの

toString()

は次のとおりです。

{Abbott and Costello=Comedy and 1940s}


5結論

このクイックチュートリアルでは、JSON形式の文字列との間でJava

Maps

をシリアル化および逆シリアル化する方法を説明しました。

いつものように、あなたはhttps://github.com/eugenp/tutorials/tree/master/jackson[Github repository]でこの記事で提供された例をチェックすることができます。