简体   繁体   English

单身人士 - 正确的方式

[英]Singleton – the proper way

public enum YourSingleton {
    INSTANCE;

    public void doStuff(String stuff) {
        System.out.println("Doing " + stuff);
    }
}

YourSingleton.INSTANCE.doStuff("some stuff");

Here is the original link, http://electrotek.wordpress.com/2008/08/06/singleton-in-java-the-proper-way/ 这是最初的链接, http://electrotek.wordpress.com/2008/08/06/singleton-in-java-the-proper-way/

I am asking why we can call the function doStuff this way in Java. 我在问为什么我们可以在Java中以这种方式调用函数doStuff。

In Java, enum can do everything that class can [1] . 在Java中, enum可以完成class所能做的所有事情[1] YourSingleton.INSTANCE creates an instance of YourSingleton , so you can then invoke methods as if it were a regular class instance, which it basically is. YourSingleton.INSTANCE创建的实例YourSingleton ,这样,那么你可以调用方法就好像它是一个普通class的实例,它基本上是。

See the official Java docs for a more in-depth discussion on Enum Types: http://download.oracle.com/javase/tutorial/java/javaOO/enum.html 有关枚举类型的更深入讨论,请参阅官方Java文档: http//download.oracle.com/javase/tutorial/java/javaOO/enum.html

[1] enum does not have a practical implementation of inheritance. [1] enum没有实际的继承实现。 Since all enum types implicity inherit java.lang.Enum and Java does not support multiple inheritance, you cannot extend anything else. 由于所有enum类型隐含继承java.lang.Enum并且Java不支持多继承,因此您无法扩展其他任何内容。

The Traditional way to implementing singleton is fine, but to maintain its Status as true singleton, it needs to protect itself from sophisticated Serialization and Reflection Attacks. 传统的实现单例的方法很好,但是要将其状态保持为真正的单例,它需要保护自己免受复杂的序列化和反射攻击。 The general way of doing this, is by making the class Implement Serializable, make all instance fields Transient and also implement a readResolve method. 这样做的一般方法是使类实现Serializable,使所有实例字段Transient并实现readResolve方法。 (that return the same singleton instance). (返回相同的单例实例)。

The Enum Singleton pattern provides all these features out of the box. Enum Singleton模式提供开箱即用的所有这些功能。 But the main reason, I like the Enum variant is its readability. 但主要原因是,我喜欢Enum变体是它的可读性。 According to me, it conveys what it does, in a much more concise fashion, than a traditional singleton.( You do not have to explain to a new developer, all the vagaries involved in serialization and how serialization might break the singleton guarantee and why you need readResolve method etc etc..) 根据我的说法,它以比传统单身人士更简洁的方式传达它所做的事情。(你不必向新开发者解释,所有涉及序列化的变幻莫测以及序列化如何打破单身保证以及为什么你需要readResolve方法等等。)

I know this is not really what you asked for but this is what I do when I need a class to be a singleton, which may help. 我知道这不是你要求的,但是当我需要一个单身成为一个单身时,这就是我所做的,这可能有所帮助。 I create one static getInstance method that either creates and returns a new instance of the class if none exist or I return the existing reference of itself, and I make the constructor for this class private. 我创建了一个静态getInstance方法,该方法创建并返回该类的新实例(如果不存在)或者返回其自身的现有引用,并且我将此类的构造函数设为private。

For example: 例如:

public class NameOfClass{
    private static NameOfClass variableReferencingThisClass=new NameOfThisClass();

    private NameOfClass(){}

    public static NameOfClass getInstance(){
        return variableReferencingThisClass;
    }
}

You can also use the double-lock singleton creation. 您还可以使用双锁单例创建。 Assuming the class is MyObject , has a private constructor, and has a declared a static field instance as null. 假设该类是MyObject ,具有private构造函数,并且声明了一个static字段instance为null。 However, this is not a guarantee that 2 singletons will not end up getting created, but is a much closer attempt to thread safety than a single check. 然而,这并不能保证2个单身人士最终不会被创造出来,而是比单一检查更接近线程安全的尝试。

public static MyObject getInstance()
{
  if (instance == null)
  {
    synchronized(MyObject.class) {  
      if (instance == null)          
        instance = new MyObject(); 
    }
  }
  return instance;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM