创建型模式-单例模式
单例模式
单例模式是一种创建型模式,也就是创建类的实例对象的一种模式,单例模式是指一个类的实例对象只能创建一个,并提供访问该实例的全局方法。
常见的实现方式:
1. 饿汉式
饿汉式:不管是否使用都会创建实例对象。
1.1 静态常量
public class SingletonTest1 {
private static final SingletonTest1 SINGLETON_TEST_1 = new SingletonTest1();
private SingletonTest1(){
}
public static SingletonTest1 getInstance(){
return SINGLETON_TEST_1;
}
}
优点:
- 线程安全
- 类加载时就完成了实例化
缺点:
- 不使用该实例对象时,可能会造成内存浪费
1.2 静态代码块
public class SingletonTest2 {
private static final SingletonTest2 SINGLETON_TEST_2;
static {
SINGLETON_TEST_2 = new SingletonTest2();
}
private SingletonTest2(){
}
public static SingletonTest2 getInstance(){
return SINGLETON_TEST_2;
}
}
这种方式和静态变量方式类似,优缺点相同。
1.3 枚举
public enum SingletonTest7 {
INSTANCE;
public void method(){
}
}
优点:
- 线程安全
- 防止反序列化创建新的对象(其他方式不能)
2. 懒汉式
懒汉式:只有用到的时候才会创建实例对象。
2.1 线程不安全
public class SingletonTest3 {
private static SingletonTest3 SINGLETON_TEST_3;
private SingletonTest3(){
}
public static SingletonTest3 getInstance(){
if(SINGLETON_TEST_3 == null){
SINGLETON_TEST_3 = new SingletonTest3();
}
return SINGLETON_TEST_3;
}
}
优点:
- 延迟加载,避免内存浪费
缺点:
- 线程不安全
2.2 同步方法-线程安全
public class SingletonTest4 {
private static SingletonTest4 SINGLETON_TEST_4;
private SingletonTest4(){
}
public synchronized static SingletonTest4 getInstance(){
if(SINGLETON_TEST_4 == null){
SINGLETON_TEST_4 = new SingletonTest4();
}
return SINGLETON_TEST_4;
}
}
优点:
- 延迟加载,避免内存浪费
- 线程安全
缺点:
- 效率低,每个线程获取实例对象都需要获得锁
2.3 双重检查锁(DCL)--推荐使用
public class SingletonTest5 {
//volatile防止创建对象时指令重排
private static volatile SingletonTest5 SINGLETON_TEST_5;
private SingletonTest5(){
}
public static SingletonTest5 getInstance(){
if(SINGLETON_TEST_5 == null){
synchronized (SingletonTest5.class){
if(SINGLETON_TEST_5 == null){
SINGLETON_TEST_5 = new SingletonTest5();
}
}
}
return SINGLETON_TEST_5;
}
}
优点:
- 延迟加载
- 线程安全
- 效率高
2.4 静态内部类--推荐使用
public class SingletonTest6 {
private SingletonTest6(){
}
private static class SingleInstance{
private static final SingletonTest6 SINGLETON_TEST_6 = new SingletonTest6();
}
public static SingletonTest6 getInstance(){
return SingleInstance.SINGLETON_TEST_6;
}
}
优点:
- 延迟加载
- 线程安全
- 效率高
单例模式保证系统内存中类的实例对象只有一个,节省系统资源。
单例模式的使用场景:
- 需要频繁创建和销毁的对象
- 创建对象耗时或者耗费资源过多,但经常使用的对象
例如:工具类对象、文件对象、数据库数据源