Java序列化问题,同时使用guava Lists.transform

我不得不序列化一个复杂的对象,但它的一个组件是不可序列化的(第三方图形对象),所以我创建了这个Graph类的自定义可序列化版本,并使用Guava List转换将非可序列化对象转换为自定义对象。 序列化writeObject仍然失败。 我有兴趣知道为什么吗? 我的假设是Lists.transform执行Lazily操作(保持对原始对象的隐藏引用。)

还有一个解决这个问题的方法吗?

你怀疑Lists.transform()确实懒散地执行。 你可以做其中一个

Lists.newArrayList(Lists.transform(...)) 

或者,如果你想要一个不可变的版本,

 ImmutableList.copyOf(Lists.transform(...)) 

然后序列化结果列表。

Lists.transform()返回原始列表的变换视图。 来自Lists.transform() javadoc :

返回的列表始终实现Serializable,但只有当fromList和function可序列化时,序列化才会成功。

序列化转换后的视图时,实际上是序列化原始列表和函数。 在您的情况下,它失败,因为您的原始列表不可序列化(因为它包含不可序列化的图形元素)。 但它也可能失败,因为该函数不实现可序列化。

顺便说一句,有一个小技巧来创建可序列化的function而没有冗长。 而不是做:

  private static final class MyFunction extends Function implements Serializable { private static final MyFunction INSTANCE = new MyFunction(); @Override public String apply(String input) { return "[" + input + "]"; } private Object readResolve() { return INSTANCE; } private static final long serialVersionUID = 1; } 

你可以使用枚举单例模式,这种模式不那么冗长,并且可以免费获得序列化(因为枚举是可序列化的)。 它还确保您的Function是一个单例:

  // enum singleton pattern private enum MyFunction implements Function { INSTANCE; @Override public String apply(String input) { return "[" + input + "]"; } } 

如果您尝试序列化从Lists#transform返回的列表,则接口List本身不是 Serializable。