• 一个类只能有一个实例

    • 构造器私有化
  • 必须自行创建这个实例

    • 含有一个该类的静态变量来保存这个唯一的实例
  • 必须自行向整个系统提供这个实例

    • 对外提供获取该实例对象的方式

      • 直接暴露
      • 用静态变量的get方法获取

几种常见形式:

  • 饿汉式:直接创建对象,不存在线程安全问题

    • 直接实例化饿汉式(间接直观)
    public class Singleton01 {
        public static final Singleton01 INSTANCE = new Singleton01();
        private Singleton01(){}
    }
    • 枚举式(最简洁)
    public enum  Singleton03 {
        INSTANCE;
    }
    • 静态代码块饿汉式(适合复杂实例化)
    public class Singleton02 {
        private Singleton02(){}
         public final static Singleton02 INSTANCE ;
        static {
          // 可以在静态代码块中添加一些逻辑代码,并将一些参数传入构造函数中
            INSTANCE = new Singleton02();
        }
    }
  • 懒汉式:延迟创建对象

    • 线程不安全(适用于单线程)
    • 线程安全(适用于多线程)
    
    public class Singleton01 {
        //volatie关键字用于防止指令重排
        private volatile static Singleton01 INSTANCE ;
        private Singleton01 (){}
        public Singleton01 getInstance(){
            // 判断是否存在INSTANCE
            if (INSTANCE == null){
                //不存在,加锁创建
                synchronized (Singleton01.class){
                    if (INSTANCE == null){
                        new Singleton01();
                    }
                }
            }
            return INSTANCE;
        }
    }
  • 静态内部类形式(适用于多线程 )

    内部类被加载和初始化才创建INSTANCE实例对象

    静态内部类不会自动随着外部类的加载和初始化而初始化,它是单独地去加载和初始化

    因为是在内部类加载和初始化时,创建的,因此是线程安全的。

    public class Singleton02 {
        private Singleton02(){}
        private static class Inner{
           public static  Singleton02 INSTANCE = new Singleton02();
        }
        public Singleton02 getINSTANCE(){
            return Inner.INSTANCE;
        }
    }

总结:

如果是饿汉式,枚举类形式最简单

如果是懒汉式,静态内部类形式最简单


林慫慫
11 声望0 粉丝

« 上一篇
java锁机制
下一篇 »
TreeMap

引用和评论

0 条评论