PareekSandeep
PareekSandeep

Reputation: 430

What is the best way to implement Singleton pattern combined with Factory pattern in Java? Detail in description

I am learning design patterns for JAVA. I wanted to use factory pattern with singleton. Now I am not sure If I went with correct approach or not.

Let me share what I have tried first. I have used Button as example class. Aim is to get singleInstance of Button and then get it's color. Can anyone let me know if it's usable in actual implementation? Am I missing on anything or on a better approach?

Here's my code:

Button.java

public abstract class Button {
    abstract void getButton();
}

ButtonClientClass.java

public class ButtonClientClass {
public static void main(String[] args){
    Button red = ButtonFactory.getButton("RedButton");
    red.getButton();
    System.out.println("hashcode"+red.hashCode());
    Button red2 = ButtonFactory.getButton("RedButton");
    System.out.println("hashcode"+red2.hashCode());

    Button green = ButtonFactory.getButton("GreenButton");
    green.getButton();
    System.out.println("hashcode"+green.hashCode());
    Button green2= ButtonFactory.getButton("GreenButton");
    System.out.println("hashcode"+green2.hashCode());
}
}

ButtonFactory.java

public class ButtonFactory {
public static Button getButton(String button){
    if(button.equals("RedButton")){
        return RedButton.getSingleRedButton();      
    }else{
        return GreenButton.getSingleGreenButton();
    }
}
}

GreenButton.java

public class GreenButton extends Button{

    private static class GreenButtonHolder {
        public static GreenButton INSTANCE = new GreenButton();
    }
    private GreenButton(){}
    public static GreenButton getSingleGreenButton(){
        return GreenButtonHolder.INSTANCE;
    }
    @Override
    void getButton() {
    System.out.println("You have a GreenButton");   
    }
}

RedButton.java

public class RedButton extends Button{
    private static class RedButtonHolder{
        public static RedButton INSTANCE = new RedButton();
    }
    private RedButton(){ }
    public static RedButton getSingleRedButton(){
        return RedButtonHolder.INSTANCE;
    }
    @Override
    void getButton() {
        System.out.println("You have a RedButton"); 
    }
}

Upvotes: 0

Views: 705

Answers (2)

Bohemian
Bohemian

Reputation: 425438

Enums are singletons, so:

public enum Button {
    RedButton() {
        public void doSomething() {
            // whatever
        }
    },
    GreenButton() {
        public void doSomething() {
            // whatever else
        }
    };
    public void getButton() {
        System.out.println("You have a " + name());
    }
    public abstract void doSomething();
}

Enums can have fields too, and in most ways are just like a normal class. Their main restriction is that they can't extend classes, but can implement interfaces.

Upvotes: 2

Jakub Ch.
Jakub Ch.

Reputation: 3727

Using enum is the simplest way to implement singleton. JVM will ensure the instance is only one without any necessary effort. That's why it's also safer way. Your example could looks like:

Button.java

public interface Button {
    void printButton();
}

GreenButton.java

public enum GreenButton implements Button {
    INSTANCE;

    @Override
    public void printButton() {
        System.out.println("Green button");
    }
}

RedButton.java

public enum RedButton implements Button {
    INSTANCE;

    @Override
    public void getButton() {
        System.out.println("Red button");
    }
}

ButtonFactory.java

public ButtonFactory {

    /*
    * In such situation, where you select one from few states (like you do for colors)
    * it's also better to use enum instead of String. It's more convenient to reuse your code. 
    */
    public static Button getButton(ButtonType type) {
        if (type == ButtonType.GREEN)
            return GreenButton.INSTANCE;
        if (type == ButtonType.RED)
            return RedButton.INSTANCE;
    }

    public static enum ButtonType {
        GREEN, RED;
    }
}

Upvotes: 2

Related Questions