Gson反序列化的工作方式很奇怪

anhgbhbe  于 2022-11-06  发布在  其他
关注(0)|答案(1)|浏览(167)

今天我发现了一些奇怪的行为Gson。

{
    "a": {
        "foo": 123
    }
}

用相应的类表示

class A(val foo: Int)

class B(val a: A) {
    val foo = a.foo
}

但是,请注意,AfooB中有一个“快捷方式”。问题是在GSON反序列化期间,这个字段没有初始化。这意味着assertEquals(123, b.foo)失败。
首先,我查看了生成的字节码,对其进行了反编译,但看起来没什么问题:

public static final class A {
      private final int foo;

      public final int getFoo() {
         return this.foo;
      }

      public A(int foo) {
         this.foo = foo;
      }
   }

public static final class B {
      private final int foo;
      @NotNull
      private final SubscriptionChangeTest.A a;

      public final int getFoo() {
         return this.foo;
      }

      @NotNull
      public final SubscriptionChangeTest.A getA() {
         return this.a;
      }

      public B(@NotNull SubscriptionChangeTest.A a) {
         Intrinsics.checkNotNullParameter(a, "a");
         super();
         this.a = a;
         this.foo = this.a.getFoo();
      }
   }

我看到的唯一原因是GSON没有调用构造函数,而是在对象创建后使用反射填充那些final字段。如果您愿意分享您对它的想法,我将不胜感激。提前感谢。

P.S他们的问题不是如何修复它,它很简单(将www.example.com更改B.foo为getter属性),而是它为什么会以这样的方式工作

2vuwiymt

2vuwiymt1#

事实证明,Gson并不调用构造函数,而是使用sun.misc.unsafe创建对象。

相关问题