Java 重新初始化瞬态变量的正确方法

Java 重新初始化瞬态变量的正确方法,java,serialization,Java,Serialization,假设一个简单的可序列化对象,如下所示: public class MySerializable implements Serializable{ String value; transient String test = "default"; public MySerializable() { test = "init"; } } private String getTest(){ test = test==null?"default"

假设一个简单的可序列化对象,如下所示:

public class MySerializable implements Serializable{
    String value;
    transient String test = "default";

    public MySerializable() {
        test = "init";
    }
}
private String getTest(){
    test = test==null?"default":test;
    return test;
}
如果此实例已序列化且未序列化,则变量
test
仍为
null
。我的方法是编写一个新方法,如下所示:

public class MySerializable implements Serializable{
    String value;
    transient String test = "default";

    public MySerializable() {
        test = "init";
    }
}
private String getTest(){
    test = test==null?"default":test;
    return test;
}
每次调用
test
变量时都调用它

有更好(更漂亮)的解决方案吗?

来自以下文档:

在序列化和反序列化过程中需要特殊处理的类必须使用以下精确签名实现特殊方法:

private void writeObject(java.io.ObjectOutputStream out)
    throws IOException
private void readObject(java.io.ObjectInputStream in)
    throws IOException, ClassNotFoundException;
private void readObjectNoData()
    throws ObjectStreamException;
[……]

readObject
方法负责从流中读取并恢复类字段。它可以调用.defaultReadObject中的
来调用默认机制来恢复对象的非静态和非瞬态字段。
defaultReadObject
方法使用流中的信息将保存在流中的对象的字段与当前对象中相应命名的字段分配。这将处理类进化为添加新字段的情况。该方法不需要关心属于其超类或子类的状态。通过使用
writeObject
方法或使用
DataOutput
支持的基本数据类型的方法将各个字段写入
ObjectOutputStream
来保存状态

所以基本上,我认为你想要:

public class MySerializable implements Serializable{
    String value;
    transient String test = "default";
    
    public MySerializable() {
        test = "init";
    }

    private void readObject(java.io.ObjectInputStream in)
         throws IOException, ClassNotFoundException {
        in.defaultReadObject();
        test = "init";
    }
}
从以下文件:

在序列化和反序列化过程中需要特殊处理的类必须使用以下精确签名实现特殊方法:

private void writeObject(java.io.ObjectOutputStream out)
    throws IOException
private void readObject(java.io.ObjectInputStream in)
    throws IOException, ClassNotFoundException;
private void readObjectNoData()
    throws ObjectStreamException;
[……]

readObject
方法负责从流中读取并恢复类字段。它可以调用.defaultReadObject中的
来调用默认机制来恢复对象的非静态和非瞬态字段。
defaultReadObject
方法使用流中的信息将保存在流中的对象的字段与当前对象中相应命名的字段分配。这将处理类进化为添加新字段的情况。该方法不需要关心属于其超类或子类的状态。通过使用
writeObject
方法或使用
DataOutput
支持的基本数据类型的方法将各个字段写入
ObjectOutputStream
来保存状态

所以基本上,我认为你想要:

public class MySerializable implements Serializable{
    String value;
    transient String test = "default";
    
    public MySerializable() {
        test = "init";
    }

    private void readObject(java.io.ObjectInputStream in)
         throws IOException, ClassNotFoundException {
        in.defaultReadObject();
        test = "init";
    }
}