在Serializable类中使用transient关键字

时间:2013-08-03 16:52:22

标签: java serializable transient

在未实现transient的类中使用Serializable关键字是否有意义?

因为Serializable仍然可以序列化未实现ObjectOutputStream的类。

5 个答案:

答案 0 :(得分:4)

由于多种原因,您可能仍希望将其标记为瞬态。立刻想到的两个是:

  • 它可以帮助传达该领域的语义目的。即,它可以帮助任何阅读代码的人理解

  • 的变量
  • 第三方库可能会使用该关键字。例如,Google的Gson库可以将任何对象序列化/反序列化为JSON,无论它是否实现Serializable。在这种情况下,Gson将(默认情况下)跳过标记为瞬态的字段。

答案 1 :(得分:2)

因为对象序列化比Serializable的简单实现更复杂(考虑代理:代理对象可以实现Serializable,但不是原始对象,在代码中仍然使用原始类)
另一种实现序列化的方法是可外部化的界面,可以完全控制对象序列化或(来自javadoc):
在序列化期间需要特殊处理的类 反序列化过程必须实现具有这些确切签名的特殊方法:

private void readObject(java.io.ObjectInputStream stream) throws IOException, ClassNotFoundException;
private void writeObject(java.io.ObjectOutputStream stream) throws IOException
private void readObjectNoData() throws ObjectStreamException;

查看ObjectOutputStream javadoc以获取有关序列化过程/机制的更多信息。

编辑:回答你的问题,transient是仅在序列化上下文中使用的关键字,因此具有瞬态字段的非Serializable对象没有意义

答案 2 :(得分:1)

  

因为Serializable仍然可以序列化未实现ObjectOutputStream的类。

这是不正确的。这会抛出一个NotSerializableException


writeObject()Object而不是Serializable的原因是签名来自实现独立于序列化定义的接口ObjectOutput。但是,它会阻止ObjectOutputStream更改其签名。

public interface ObjectOutput {
  // ...
  void writeObject(Object obj);
}

答案 3 :(得分:1)

通常,如果超类实现Serializable,它的子类也是可序列化的。这是唯一可以使字段成为瞬态并且类不直接实现Serializable的情况,但如果类是不可序列化使它们成为瞬态是没有意义的。

答案 4 :(得分:0)

不,这没有道理。

class State {
    // The 'transient' modifier has no effect here because
    // the 'State' class does not implement 'Serializable'.
    private transient int[] stateData;
}