What Is the Best Approach for Using an Enum as a Singleton in Java

What is the best approach for using an Enum as a singleton in Java?

Suppose you're binding to something which will use the properties of any object it's given - you can pass Elvis.INSTANCE very easily, but you can't pass Elvis.class and expect it to find the property (unless it's deliberately coded to find static properties of classes).

Basically you only use the singleton pattern when you want an instance. If static methods work okay for you, then just use those and don't bother with the enum.

advantage of enum over class in singleton pattern

As explained by Joshua Bloch, the two approaches are functionally identical if your singleton is not serializable. Although you may wish to add code to your private Singleton constructor to prevent reflection being used to create a second instance.

If your singleton is serializable, then the enum approach will provide all the necessary plumbing for free, whereas with the static field approach, you have to add that yourself.

In my view, there is no downside to adopting the enum approach.

Why is enum the best implementation for a singleton?

this seems like a trade-off to achieve on the fly serialization

For me it's a lot simpler and more concise to write something like

enum Singleton {
INSTANCE;
}

If you have a need to write a lot more code or introduce complexity then do so, but this is rarely required IMHO.

you lose the more friendly OOP approach of a classical singleton.

I find using fields to be simpler.

Enums can't be inherited,

True, but having multiple singletons is suspect in itself. Enums can inherit from interfaces which allows you to swap one implementation for another.

If you want to provide a skeleton class you need to create a helper class

A helper class doesn't have any state. A skeleton class might have some state in which case you need delegation.

BTW: You can use enum for helper classes

enum Helper {;
public static my_static_methods_here;
}

why should we accept enum as the best implementation for a singleton

I would follow the YAGNI principle. Only develop what you need, not what you imagine you might need.

Implementing Singleton with an Enum (in Java)

This,

public enum MySingleton {
INSTANCE;
}

has an implicit empty constructor. Make it explicit instead,

public enum MySingleton {
INSTANCE;
private MySingleton() {
System.out.println("Here");
}
}

If you then added another class with a main() method like

public static void main(String[] args) {
System.out.println(MySingleton.INSTANCE);
}

You would see

Here
INSTANCE

enum fields are compile time constants, but they are instances of their enum type. And, they're constructed when the enum type is referenced for the first time.

How to create a singleton class using enum

The differences between a class and an enum are not so big. I changed the first line of code to public enum instead of public class and added the name of your instance.

public enum Employee { // changed "class" to "enum"

INSTANCE; // added name of the (single) instance

private int id;
private String name;
Employee() {} // removed "public"
public int getId() {
return id;
}
public void setId( int id ) {
this.id = id;
}
public String getName() {
return name;
}
public void setName( String name ) {
this.name = name;
}
}

Please keep in mind, that singeltons, enum instances, static things might hinder you later on, if you want to run your code several times in one vm. Consider creating an instance of Employee in your main class and pass it through your application.

Beside that, enums have some other special features:

  • You cannot extend another class (only implements)
  • Some predefined methods (like static values() and getName()) are available
  • constructors can only be package private, or private

What is an efficient way to implement a singleton pattern in Java?

Use an enum:

public enum Foo {
INSTANCE;
}

Joshua Bloch explained this approach in his Effective Java Reloaded talk at Google I/O 2008: link to video. Also see slides 30-32 of his presentation (effective_java_reloaded.pdf):

The Right Way to Implement a Serializable Singleton

public enum Elvis {
INSTANCE;
private final String[] favoriteSongs =
{ "Hound Dog", "Heartbreak Hotel" };
public void printFavorites() {
System.out.println(Arrays.toString(favoriteSongs));
}
}

Edit: An online portion of "Effective Java" says:

"This approach is functionally equivalent to the public field approach, except that it is more concise, provides the serialization machinery for free, and provides an ironclad guarantee against multiple instantiation, even in the face of sophisticated serialization or reflection attacks. While this approach has yet to be widely adopted, a single-element enum type is the best way to implement a singleton."

How to enforce Singleton pattern using enum when class extends Another class

Since an enum is just a class, you can have it contain whatever you want (including a single instance of the "extended" class you want) and just expose it. You can control the singleton nature of anything with an enum.

public enum Elvis {

INSTANCE;

private Object wrappedObject = new Object();

public Object wrappedObject(){ return wrappedObject; }

public static void main(String args[]){
Object sortaSingledton = INSTANCE.wrappedObject();//there still can be only one
}
}

What is the use of the enum singleton in Java?

what is the use of this singleton? Why we don't use these old good static/class fields and methods?

Because enum is an object so it can not only be passed around but also implement interfaces.

Also since we are making a class, we can use the different public/private options available to all kinds of classes.

So in practice, we can make a singleton that implements an interface and then pass it around in our code and the calling code is non the wiser. We can also make the enum class package private but still pass it around to other classes in other packages that expect the interface.

If we used the static methods version, then the calling class would have to know that this object is a singleton, and our singleton class would have to be public so the other classes can see it and use it's methods.

Singleton Pattern: Using Enum Version

public enum WirelessSensorFactory {
INSTANCE;

// all the methods you want
}

Here's your singleton: an enum with only one instance.

Note that this singleton is thread-safe, while yours is not: two threads might both go into a race condition or visibility problem and both create their own instance of your singleton.



Related Topics



Leave a reply



Submit