Java 如何维护序列化对象的单例状态?

Java 如何维护序列化对象的单例状态?,java,serialization,singleton,Java,Serialization,Singleton,如果我将类“A”定义为单例,则意味着我只能创建类“A”的一个对象。如果我将其设置为可序列化并序列化,那么如何实现同一对象的单例状态?为了保证可序列化的单例的唯一性,您可能需要自定义readResolve方法来返回单例对象,而不是新反序列化的单例对象。另一方面,《有效Java》一书第77项建议: 例如,控件,首选枚举类型而不是readResolve 为了保证可序列化的单例对象的唯一性,您可能需要自定义readResolve方法来返回单例对象,而不是新反序列化的对象。另一方面,《有效Java》一书第

如果我将类“A”定义为单例,则意味着我只能创建类“A”的一个对象。如果我将其设置为可序列化并序列化,那么如何实现同一对象的单例状态?

为了保证可序列化的单例的唯一性,您可能需要自定义
readResolve
方法来返回单例对象,而不是新反序列化的单例对象。另一方面,《有效Java》一书第77项建议:

例如,控件,首选枚举类型而不是readResolve


为了保证可序列化的单例对象的唯一性,您可能需要自定义readResolve方法来返回单例对象,而不是新反序列化的对象。另一方面,《有效Java》一书第77项建议:

例如,控件,首选枚举类型而不是readResolve


引用
effectivejava#77
,您应该看看如何实现
readResolve
方法

readResolve功能允许您用另一个实例替换该实例 由readObject创建[Serialization,3.7]。如果对象的类是值得的- ized使用正确的声明定义readResolve方法,此方法为 在反序列化新创建的对象后对其调用。对象引用 然后返回此方法返回的对象,以代替新创建的对象。在里面 大多数使用此功能时,不会保留对新创建对象的引用,因此 立即成为垃圾收集的合格对象


引用
effectivejava#77
,您应该看看如何实现
readResolve
方法

readResolve功能允许您用另一个实例替换该实例 由readObject创建[Serialization,3.7]。如果对象的类是值得的- ized使用正确的声明定义readResolve方法,此方法为 在反序列化新创建的对象后对其调用。对象引用 然后返回此方法返回的对象,以代替新创建的对象。在里面 大多数使用此功能时,不会保留对新创建对象的引用,因此 立即成为垃圾收集的合格对象


在反序列化任何对象之前,调用的一个方法是readResolve(),因此我们可以简单地从该方法返回相同的状态对象,而无需实际反序列化它

请看下面

public final class MySingleton {
  private MySingleton() { }

  private static final MySingleton INSTANCE = new MySingleton();

  public static MySingleton getInstance() { return INSTANCE; }

  private Object readResolve() throws ObjectStreamException {
   // instead of the object we're on, 
   // return the class variable INSTANCE
  return INSTANCE; 
  }

}

在反序列化任何对象之前,调用的一个方法是readResolve(),因此我们可以简单地从该方法返回相同的状态对象,而无需实际反序列化它

请看下面

public final class MySingleton {
  private MySingleton() { }

  private static final MySingleton INSTANCE = new MySingleton();

  public static MySingleton getInstance() { return INSTANCE; }

  private Object readResolve() throws ObjectStreamException {
   // instead of the object we're on, 
   // return the class variable INSTANCE
  return INSTANCE; 
  }

}

在您的意思中,序列化过程是如何与单例概念交叉的?如果我序列化任何对象意味着我保存了对象的状态,那么我反序列化了它,我得到了具有相同状态的新对象,但它仍然是一个新对象,那么我如何实现单例状态?所以有两个对象,一个是序列化对象,另一个在上下文中。在反序列化任何对象之前,调用一个方法是readResolve,这样我们就可以简单地从该方法返回同一个对象。在您的意思中,序列化过程如何与Singleton概念交叉?如果我序列化了任何对象,就意味着我保存了对象的状态,然后我反序列化了它,我得到了具有相同状态的新对象,但它仍然是一个新对象,那么如何实现单例状态呢?所以有两个对象,一个是序列化对象,另一个在上下文中。在反序列化任何对象之前,调用一个方法是readResolve,这样我们就可以从这个方法返回同一个对象。是的,这是真的,我只是在尝试这个方法,在反序列化任何对象之前,调用的一个方法是readResolve,因此我们可以简单地从该方法返回相同的对象。非常感谢。@AmolFasale,好的。但我强烈建议您阅读“有效Java”(第二版)第77项(第308页)。是的,这是真的,我只是在尝试这一项,在反序列化任何对象之前,调用一个方法的是readResolve,因此我们可以简单地从这个方法返回相同的对象。非常感谢。@AmolFasale,好的。但我强烈建议您阅读“有效Java”(第二版)第77项(第308页)。谢谢Manoj,它真的很有用。谢谢Manoj,它真的很有用。