设计模式——单例模式(代码实现)

单例模式主要用来产生一个对象的具体实例,它可以确保系统中一个类只产生一个实例。

两个好处:

  • 对于频繁使用的对象,可以省略new操作花费的时间
  • new的次数少了,对系统内存的使用频率就小了,那么GC压力就会降低,缩短了GC停顿时间

饿汉式单例模式:

public class Singleton {
    private Singleton() {
        System.out.println("Singleton iscreate");
    }

    private static Singleton instance = new Singleton();

    private static Singleton getInstance() {
        return instance;
    }
}

私有化构造方法的作用:不能new这个类的实例,从而避免该类被错误的创建

因此要想获取这个对象,只能调用getInstance()工厂方法,构造方法被私有化,要想这个方法可以被调用,所以这个方法必须用static修饰,调用方式:类.方法名

从而instance也必须用static修饰。

好处:性能非常好,getInstance()方法只是简单的返回instance,并没有任何锁操作,所以在并行程序中它会有很好的表现

坏处:Singleton构造函数或者说Singleton实例在什么时候创建是不受控制的,对于静态成员instance,它会在类第一次初始化的时候被创建,并不是第一次调用getInstance()方法的时候被创建的

延伸一点:static修饰的成员变量所属类被加载的时候,变量间会被分配空间,及就会被创建

懒汉式单例模式:

public class LazySingleton {

    private LazySingleton() {
        System.out.println("LazySingleton is create");
    }

    private static LazySingleton instance = null;

    private static synchronized LazySingleton getInstance() {
        if (instance == null)
            instance = new LazySingleton();
        return instance;
    }
}

私有化构造方法的作用:不能new这个类的实例,从而避免该类被错误的创建

只有当调用getInstance()方法时才会创建单例对象,为了防止对象被多次创建,还须要使用synchronized进行方法同步

好处:充分利用了延迟加载,只有在真正需要时才会创建对象

坏处:并发环境下加锁,竞争激烈的场合对性能会产生一定影响

另外还有一种,双重判断加双同步(安全又高效):

public class SingleTon {

    private static volatile SingleTon singleTon = null;

    private SingleTon() {

    }

    public static SingleTon getInstance() {
        if (singleTon == null) {
            synchronized (SingleTon.class) {
                if (singleTon == null) {
                    singleTon = new SingleTon();
                }
            }
        }
        return singleTon;
    }
}
为什么双重判断:
如果单层if判断,在服务器允许的情况下,假设有一百个线程,耗费的时间为100*(同步判断时间+if判断时间),而如果双重if判断,100的线程可以同时if判断,理论消耗的时间只有一个if判断的时间。
所以如果面对高并发的情况,而且采用的是懒汉模式,最好的选择就是双重判断加同步的方式。
原文地址:https://www.cnblogs.com/java-spring/p/9075670.html