Gson 的自定义序列化器和反序列化器可以得到 class/field 吗?

Can Gson's custom serializers and deserializers get the class/field?

我正在考虑切换到 Gson。

根据我的初学者知识,我知道两种实现自定义序列化器和反序列化器的方法:

  1. JsonSerializerJsonDeserializer,以及
  2. TypeAdaptor.

考虑以下因素:

public class Pojo {
  @JsonAdaptor(MyCustomAdaptor.class)
  private Integer number;
}

class MyCustomAdaptor extends TypeAdaptor<Integer> {
  @Override
  public Integer read(JsonReader in) throws IOException {
    // ...
  }

  public void write(JsonWriter writer, Integer value) throws IOException {
    // ...
  }
}

我注意到 TypeAdaptor 没有暴露 numberFieldJsonSerializerJsonDeserializer 也不是这种情况。我明白,当这些 类 在 marshaling/unmarshalling 生命周期中被使用时,就不需要知道这些信息了。

暂时,让我们假装 FieldTypeAdaptor 秒内暴露。以下是我将要执行的操作的基本示例:

public class Pojo {
  @JsonAdaptor(MyCustomAdaptor.class)
  @FloatSerialize
  private Number number;
}

class MyCustomAdaptor extends TypeAdaptor<Number> {
  @Override
  public Number read(JsonReader in, Field field) throws IOException {
    // Do something if @FloatSerialize is present.
  }

  public void write(JsonWriter writer, Number value, Field field) throws IOException {
    // Do something if @FloatSerialize is present.
  }
}

我知道这没有意义,因为 @JsonAdaptor 可用于 类 和字段。

另外,我知道有更好的方法来完成上面的例子;这只是一个例子,没有意义。基本上,我想在每个字段的基础上使用注释来告诉自定义 serializers/deserializers 如何处理。

Gson 可以吗?你能创建一个自定义 serializer/deserializer 来公开带注释的 class/field/etc 吗?

@JsonAdaptor(MyCustomAdaptor.class)
private Integer number;

您已经注释了一个整数字段。

I noticed that TypeAdaptor does not expose the Field of number

我觉得你理解错了。

你提供 TypeAdaptor,你给它的类型与你的字段相同:

class MyCustomAdaptor extends TypeAdaptor<Integer>

然后在序列化时,您将注释为输入的 java 对象序列化为字符串,然后您的字段可直接作为参数中的 'value' 使用:

public void write(JsonWriter writer, Integer value) throws IOException

在反序列化时,您有一个 json 字符串作为输入以反序列化为您已注释的对象。在类型适配器中,此对象是您的字段,这就是读取方法 return an Integer.

的原因

Integer read(JsonReader in) throws IOException

return 来自 JsonReader 的整数由您决定。

您可以在您的字段中使用数字而不是整数,然后您可以在您的字段中使用浮点数、整数、短整数等等。

为此你带上一个 NumberAdaptor:

class MyCustomAdaptor extends TypeAdaptor<Number> {
   
    Number read(JsonReader in, Field field) throws IOException;
    
    void write(JsonWriter writer, Number value) throws IOException; 
}

如果真的要考虑'field',那就给整个objet提供一个适配器:

class Pojo Adaptor extends TypeAdaptor< Pojo > {

  Pojo read(JsonReader in) throws IOException;

  void write(JsonWriter writer, Pojo value) throws IOException;
}

然后您就可以访问适配器中的整个对象及其字段。

形式相同 JsonSerializer/JsonDeserialize。

加上你的额外信息:

class Pojo Adaptor extends TypeAdaptor< Pojo > {

  Pojo read(JsonReader in) throws IOException{
for(Field f: Pojo.class.getDeclaredFields()){
            f.steAccessible();
            for(Annotation a : f.getAnnotations()){
                // Do what you want here withe the field and its annotation
            }
    }

  void write(JsonWriter writer, Pojo value) throws IOException{

        for(Field f: Pojo.class.getDeclaredFields()){
            f.steAccessible();
            for(Annotation a : f.getAnnotations()){
                // Do what you want here with the field and its annotation
            }
        }
    }
}

这是我凭记忆写的,但你明白了