一、单例的由来
在我们的程序中,如果需要多个线程操作同一对象,需要保证对象的唯一性。如何保证唯一性呢?
二、解决的问题
对象实例化过程中,只实例化一次
三、解决的思路
有一个实例化过程(仅仅只有一次),提供返回实例的方法
四、单例模式的分类
我们从几个方面考虑单例模型的性能:安全性、
1、饿汉式
public class HungrySingleton {
// 加载的时候产生实例对象
private static HungrySingleton instance = new HungrySingleton();
private HungrySingleton() {}
// 返回实例对象
public static HungrySingleton getInstance() {
return instance;
}
}
输出结果:
安全性:加载的时候已经被实例化,所以只有这一次,线程安全的。
懒加载:没有延迟加载。
性能:比较好
2、懒汉式
public class HoomSingleton {
private static HoomSingleton instance = null;
rivate HoomSingleton() {}
public static HoomSingleton getInstance() {
if (null == instance) {
instance = new HoomSingleton();
}
return instance;
}
}
线程安全:不能保证实例对象的唯一性
3、懒汉式+同步方法
public class HoomSynSingleton {
private static HoomSynSingleton instance = null;
private HoomSynSingleton() {}
public synchronized static HoomSynSingleton getInstance() {
if (null == instance) {
instance = new HoomSynSingleton();
}
return instance;
}
}
性能安全:安全
懒加载
性能:synchronized退化到了串行执行
4、DCL并发模式
// double-check-locking
public class DCL {
private static DCL instance = null;
private DCL() {}
public static DCL getInstance() {
if (null == instance) {
synchronized (DCL.class) {
if (null == instance)
instance = new DCL();
}
}
return instance;
}
线程安全
懒加载
性能比较好
5、Holder
声明类的时候,成员变量中不声明实例变量,而放到内部静态类中。
一种广泛使用的一个单例方式。
public class HolderDemo {
private HolderDemo() {}
private static class Holder {
private static HolderDemo instance = new HolderDemo();
}
// 懒加载
// synchronized
public static HolderDemo getInstance() {
return Holder.instance;
}
}