为什么反序列化后lambda更改Class?

时间:2018-07-04 14:53:43

标签: java lambda type-safety

我需要弄清楚两个给定的接口实现是否相同。我幼稚的方法是大致通过以下方式测试其类的相等性: first.getClass().equals(second.getClass())。它一直有效,直到我的代码遇到(反)序列化的lambda表达式。在反序列化期间,它们似乎更改了Class实例。以下示例说明了这种情况:

public interface SerializableSupplier<T> extends Serializable{
   T get();
}

private static final SerializableSupplier<Integer> FINAL_SUPPLIER = () -> 8;

public static void main(String args[]) throws IOException, ClassNotFoundException {


   ByteArrayOutputStream outStr = new ByteArrayOutputStream();
   ObjectOutputStream oss = new ObjectOutputStream(outStr);

   oss.writeObject(FINAL_SUPPLIER);
   oss.flush();
   oss.close();

   ObjectInputStream ois = new ObjectInputStream(new ByteArrayInputStream(outStr.toByteArray()));
   SerializableSupplier<Integer> supplierDeserialized = (SerializableSupplier<Integer>) ois.readObject();

   System.out.println(FINAL_SUPPLIER.getClass());
   System.out.println(supplierDeserialized.getClass());
   System.out.println(FINAL_SUPPLIER.getClass().equals(supplierDeserialized.getClass()));   
}

哪些印刷品:

class cz.plastique.examples.LambdaChangingClass$$Lambda$1/295530567
class cz.plastique.examples.LambdaChangingClass$$Lambda$4/1854731462
false

使用匿名实现时的行为不同:

private static final SerializableSupplier<Integer> ANONYMOUS_FINAL_SUPPLIER =
new SerializableSupplier<Integer>() {
   @Override
   public Integer get() {
     return 8;
   }
};

哪些印刷品:

class cz.plastique.examples.LambdaChangingClass$1
class cz.plastique.examples.LambdaChangingClass$1
true

我对此感到困惑。为什么lambda更改其类?甚至在序列化之后,只要两个给定的接口实现都相同,a'还能如何识别?

我想这与runtime lambda object construction有关。但是我不知道它是如何发生的以及为什么发生?

Full example code.

0 个答案:

没有答案