其他分享
首页 > 其他分享> > 单例模式实现(七种)

单例模式实现(七种)

作者:互联网

文章目录

1、什么是单例模式

单例模式确保一个类只有一个实例,并提供一个全局访问点,实现单例模式的方法是私有化构造函数,通过getInstance()方法实例化对象,并返回这个实例

保证在JVM中只有一个实例

2、单例模式优缺点

优点:
1、单例类只有一个实例
2、共享资源,全局使用
3、节省创建时间,提高性能

缺点:
可能存在线程不安全的问题 解决线程安全问题

3、七种方法去实现单例模式

1)饿汉式

public class Singleton {
    /**
     * 饿汉式
     * 优点:先天性线程安全,类初始化得时候该对象就被创建了
     * 缺点:饿汉式如果使用过多得话,项目在启动时候会变慢,存放在方法区占用内存
     */
    private static Singleton singleton = new Singleton();

    //构造私有化
    private Singleton() {

    }
    //只能通过该方法获得实例
    public Singleton getInstance() {
        return singleton;
    }
}

2)懒汉式(线程不安全)

/**
 * @Description: 饿汉式
 * @ClassName design_pattern
 * @Author: 王瑞文
 * @Date: 2021/1/16 20:14
 */
public class Singleton1 {
    /**
     * 懒汉式,需要使用得时候才会被初始化
     */
    private static Singleton1 singleton = null;

    //构造私有化
    private Singleton1() {

    }

    //只能通过该方法获得实例,但是在多线程的情况下可能会被初始化多次下
    public static Singleton1 getInstance() {
        //只有第一次才会被初始化
        if (singleton == null) {
            singleton = new Singleton1();
        }
        return singleton;
    }
}

3)懒汉式(线程安全)

/**
 * @Description: 饿汉式
 * @ClassName design_pattern
 * @Author: 王瑞文
 * @Date: 2021/1/16 20:14
 */
public class Singleton1 {
    /**
     * 懒汉式,需要使用得时候才会被初始化
     */
    private static Singleton1 singleton = null;

    //构造私有化
    private Singleton1() {

    }

    //只能通过该方法获得实例,但是在多线程的情况下可能会被初始化多次下
    // public synchronized static Singleton1 getInstance() { 这么去加锁的话 效率是很低的就变成了单线程但是可以去解决线程安全的问题

    public synchronized  static Singleton1 getInstance() {
        //只有第一次才会被初始化
        if (singleton == null) {
            singleton = new Singleton1();
        }
        return singleton;
    }
}

4)双重检验锁(DCL)

/**
 * @Description: 饿汉式
 * @ClassName design_pattern
 * @Author: 王瑞文
 * @Date: 2021/1/16 20:14
 */
public class Singleton2 {
    /**
     * 懒汉式,需要使用得时候才会被初始化
     */
    private static Singleton2 singleton = null;

    //构造私有化
    private Singleton2() {

    }

    //只能通过该方法获得实例,但是在多线程的情况下可能会被初始化多次下
    // public synchronized static Singleton1 getInstance() { 这么去加锁的话 效率是很低的就变成了单线程但是可以去解决线程安全的问题
    //双重检验锁,为了解决synchronized读写都加锁
    public static Singleton2 getInstance() {
        //在第一次初始化对象的时候才去加锁
        if (singleton == null) {
            synchronized (Singleton2.class) {
                if (singleton == null) //只会有一个对象进入,再次判断当前线程是不是应该去初始化对象
                    singleton = new Singleton2();
            }
        }
        return singleton;
    }
}

5)静态内部内形式

/**
 * @Description: 饿汉式
 * @ClassName design_pattern
 * @Author: 王瑞文
 * @Date: 2021/1/16 20:14
 */
public class Singleton4 {


    //构造私有化
    private Singleton4() {

    }

    //只能通过该方法获得实例
    public Singleton4 getInstance() {
        return SingletonUtils.singleton;
    }
    //静态内部类特征:继承懒汉式有点,同时解决双重检验所第一次加载慢的问题
    public static class SingletonUtils {
        private static Singleton4 singleton = new Singleton4();
    }
}

6)枚举形式

/**
 * @Description:
 * @ClassName design_pattern
 * @Author: 王瑞文
 * @Date: 2021/1/16 21:30
 */
public enum EnumSingleton {
    INSTANCE;

    // 枚举能够绝对有效的防止实例化多次,和防止反射和序列化破解
    public void test() {
        System.out.println("Test方法...");
    }
}

7)使用容器管理

public class SingletonManager {

    private static Map<String, Object> objMap = new HashMap<String, Object>();
    public static void registerService(String key, Object instance) {
        if (!objMap.containsKey(key)) {
            objMap.put(key, instance);
        }
    }
    public static Object getService(String key) {
        {
            return objMap.get(key);
        }
    }
}

使用SingletonManager 将多种单例类统一管理,在使用时根据key获取对象对应类型的对象。这种方式使得我们可以管理多种类型的单例,并且在使用时可以通过统一的接口进行获取操作,降低了用户的使用成本,也对用户隐藏了具体实现,降低了耦合度。

另外在SSM框架中我们知道把类交给IOC容器去管理的话,默认创建的也是单例模式

标签:singleton,七种,模式,static,private,单例,Singleton1,public
来源: https://blog.csdn.net/weixin_45498245/article/details/112740762