Java 单例设计模式

Singleton 单例模式是 Java 中最简单的设计模式之一。这种类型的设计模式属于创建模式,因为该模式提供了创建对象的最佳方法之一。

Java 单例模式

此模式涉及单个类,该类负责创建对象,同时确保只创建单个对象。该类提供了一种访问其唯一对象的方法,无需实例化该类的对象即可直接访问。

由于只有一个 Singleton 实例,因此每个类 Singleton 的任何实例字段只会出现一次,就像静态字段一样。单例通常控制对资源的访问,例如数据库连接或套接字。

例如,如果您的数据库只有一个连接的许可证,或者您的 JDBC 驱动程序在多线程处理方面遇到问题,单例会确保只建立一个连接,或者一次只有一个线程可以访问该连接。

单例设计模式的优点

单例设计模式可以节省内存,因为只创建一个对象实例,并且它还提供对其实例的全局访问。

使用单例设计模式

当您想要创建这样一个只有一个实例的类时,可以使用单例设计模式。主要用在多线程中,创建多线程和数据库相关的应用程序。

一些使用单例设计模式的设计:

  • 创建记录器类
  • 创建与配置管理相关的类
  • 创建与数据库连接池相关的类
  • 创建缓存机制的类

Java 单例类/设计模式:示例

示例 1

最简单的实现由私有构造函数和保存其结果的字段组成,并且名称类似于 getInstance() 的静态访问器方法。

可以从静态初始化块 或者,更简单地说,使用初始化程序。 getInstance() 方法(必须是公共的)然后简单地返回这个实例 -

package com.yxjc123;

class Singleton {

   private static Singleton singleton = new Singleton( );

   /* 私有构造函数可以防止其它的构造函数
    * 类的实例化
    */
   private Singleton() { }

   /* 静态实例方法 */
   public static Singleton getInstance( ) {
      return singleton;
   }

   /* 其它受单例保护的方法 */
   protected void demoMethod( ) {
      System.out.println("demoMethod for singleton");
   }
}
public class Tester {

   public static void main(String[] args) {
      Singleton tmp = Singleton.getInstance( );
      tmp.demoMethod( );
   }
} 

如果你编译并执行上面的程序,你将得到以下结果 

输出

demoMethod for singleton 

示例 2

以下实现展示了经典的单例设计模式。在此示例中,ClassicSingleton 类维护对单独单例实例的静态引用,并从静态 getInstance() 方法返回该引用 。

这里,ClassicSingleton 类采用了一种称为延迟实例化的技术来创建单例;因此,直到第一次调用 getInstance() 方法时才会创建单例实例。这种技术确保仅在需要时创建单例实例。

package com.yxjc123;

class ClassicSingleton {

   private static ClassicSingleton instance = null;
   private ClassicSingleton() {
      // 防止其它的构造函数实例化。
   }

   public static ClassicSingleton getInstance() {
      if(instance == null) {
         instance = new ClassicSingleton();
      }
      return instance;
   }
   
   protected void demoMethod( ) {
      System.out.println("demoMethod for singleton");
   }
}
public class Tester {

   public static void main(String[] args) {
      ClassicSingleton tmp = ClassicSingleton.getInstance( );
      tmp.demoMethod( );
   }
} 

如果编译并执行上述程序,您将得到以下结果 

输出

demoMethod for singleton 

示例 3

以下实现显示了线程安全的 Singleton 对象创建。在此示例中,ClassicSingleton 类维护对单独单例实例的静态引用,并从静态 getInstance() 返回该引用 方法,我们使用 synchronized 关键字使其成为线程安全的。

class ClassicSingleton {

   private static ClassicSingleton instance = null;
   private ClassicSingleton() {
      // 防止其它的构造函数实例化。
   }

   public static synchronized ClassicSingleton getInstance() {
      if(instance == null) {
         instance = new ClassicSingleton();
      }
      return instance;
   }
   
   protected void demoMethod( ) {
      System.out.println("demoMethod for singleton");
   }
}
public class Tester {

   public static void main(String[] args) {
      ClassicSingleton tmp = ClassicSingleton.getInstance( );
      tmp.demoMethod( );
   }
} 

如果编译并执行上述程序,您将得到以下结果

输出

demoMethod for singleton