在 Java 接口中使用单例

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/39074628/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 04:04:22  来源:igfitidea点击:

Using Singleton with Interfaces Java

javainterfacesingleton

提问by Mira Mira

i want to know, how to use the singleton pattern with interfaces? i have created a interface:

我想知道,如何在接口中使用单例模式?我创建了一个界面:

public interface BuisinessService {

   BuisinessService getInstance();

}

I make this implementation:

我做这个实现:

public class BuisinessServiceImpl implements BuisinessService {

  private static BuisinessServiceImpl instance = null;

  private BuisinessServiceImpl(){ }

  @Override
  public BuisinessServiceImpl getInstance() {
    if (instance == null) {
        BuisinessServiceImpl.instance = new BuisinessServiceImpl();
    }
    return BuisinessServiceImpl.instance;
  }
}

How can i get access to getInstance from my main-class? I tried somethink like

如何从我的主类访问 getInstance?我试过像

private BuisinessService service = new BuisinessServiceImpl();

(does not work - Constructor from BuisinessServiceImpl() is private)

(不起作用 - BuisinessServiceImpl() 的构造函数是私有的)

But what else? Can you help me out?

但还有什么?你能帮我吗?

Edit: I'm using Java Spring! I don't want to use Java Springs - Dependency Injection!

编辑:我正在使用 Java Spring!我不想使用 Java Springs - 依赖注入!

Greets, Mira

问候,米拉

回答by Danail Alexiev

The code you have provided is a bit mixed - up.

您提供的代码有点混乱。

The whole point of controlling the instantiation of your singleton class means that you have to hide your constructor, so clients can't access it and create new instance at will.

控制单例类的实例化的全部意义在于您必须隐藏构造函数,因此客户端无法访问它并随意创建新实例。

Your factory method (a method, that creates the instance of your class) getInstance()is an instance method. You have to create a new instance of BusinessServicein order to create an instance of BusinessService- it's pretty obvious that won't work properly.

您的工厂方法(创建类getInstance()的实例的方法)是实例方法。您必须创建一个新实例BusinessService才能创建 的实例BusinessService- 很明显这将无法正常工作。

You have a few options to deal with your situation:

您有几种选择来处理您的情况:

  1. Remove the getInstance()method from your interface and expose it in your implementation class as a static method. You should also limit the visibility of the constructor to private.

    public class BusinessServiceImpl implements BusinessService {
    
        public static BusinessServiceImpl getInstance() {
            // instantiation logic
        }
    
        private BusinessServiceImpl() {
            // constructor logic
        }
    }
    
  2. Use a factory class to instantiate your service and control the number of instances. This includes removing the getInstance()method all together and limiting the visibility of your BusinessServiceImplclass to package.

    class BusinessServiceImpl implements BusinessService {
    
        BusinessServiceImpl() {
            // constructor logic
        }
    }
    
    // should be in the same package as BusinessServiceImpl
    public final class BusinessServiceFactory {
    
        private BusinessServiceImpl instance;
    
        public BusinessService getInstance() {
            // instance creation logic, same as singleton creation logic
        }
    
    }
    
  3. Use an enum to deal with the singleton logic. Remove the getInstance()method from your interface.

    public enum BusinessServiceImpl implements BusinessService {
    
        INSTANCE;
    
        // implement the methods from your interface
    }
    
  1. getInstance()从您的接口中删除该方法并将其作为静态方法公开在您的实现类中。您还应该将构造函数的可见性限制为private.

    public class BusinessServiceImpl implements BusinessService {
    
        public static BusinessServiceImpl getInstance() {
            // instantiation logic
        }
    
        private BusinessServiceImpl() {
            // constructor logic
        }
    }
    
  2. 使用工厂类来实例化您的服务并控制实例的数量。这包括getInstance()一起删除该方法并将您的BusinessServiceImpl类的可见性限制为package.

    class BusinessServiceImpl implements BusinessService {
    
        BusinessServiceImpl() {
            // constructor logic
        }
    }
    
    // should be in the same package as BusinessServiceImpl
    public final class BusinessServiceFactory {
    
        private BusinessServiceImpl instance;
    
        public BusinessService getInstance() {
            // instance creation logic, same as singleton creation logic
        }
    
    }
    
  3. 使用枚举来处理单例逻辑。getInstance()从您的界面中删除该方法。

    public enum BusinessServiceImpl implements BusinessService {
    
        INSTANCE;
    
        // implement the methods from your interface
    }