你知道单例模式几种写法吗?
我们知道Java中有23种设计模式,单例模式是其中的一种,你知道单例模式有几种写法吗?
1.饿汉式
public class Singleton_1 {private static final Singleton_1 INSTANCE = new Singleton_1();private Singleton_1(){}public Singleton_1 getInstance(){return INSTANCE;}}
优点:最简单的写法
缺点:无论使用或者不使用都会给它分配出一块内存出来
2.静态代码块方式
public class Singleton_2 {private static Singleton_2 Instance;static {Instance = new Singleton_2();}private Singleton_2(){}public static Singleton_2 getInstance(){return Instance;}}
优点:简单快捷
缺点:浪费内存
3.懒汉式
public class Singleton_3 {private static Singleton_3 INSTANCE = null;private Singleton_3() {}public static Singleton_3 getInstance(){if(INSTANCE==null){return new Singleton_3();}return INSTANCE;}}
优点:与饿汉式相比,在不用的情况下不会分配出内存了,只有在用的情况下,getInstance方法才会new出该对象
缺点:线程不安全,当第一个线程走到if时,第二个线程也走到if并且继续往下执行了,这样第一个线程也会继续往下走,会出现多个对象。
4.方法加锁
public class Singleton_4 {private static Singleton_4 INSTANCE = null;private Singleton_4() {}public static synchronized Singleton_4 getInstance(){if(INSTANCE==null){return new Singleton_4();}return INSTANCE;}}
优点:线程安全
缺点:synchronized锁的范围太大了,因为只需要锁住return new Singleton_3();即可
5.方法内加锁并检查:
public class Singleton_5 {private static Singleton_5 instance = null;private Singleton_5() {}public static Singleton_5 getInstance() {if (instance == null) {synchronized (Singleton_5.class) {instance = new Singleton_5();}}return instance;}}
优点:synchronized锁的范围小了
缺点:线程不完全,当两个线程同时到if是判断对象为null,两个线程同时去if里面抢锁,最终两个线程都会走完里面的代码,new出两个不同的对象。
6.方法内加锁双重检查
public class Singleton_6 {private volatile static Singleton_6 instance = null;private Singleton_6(){}public static Singleton_6 getInstance(){if(instance==null){synchronized (Singleton_5.class){if(instance==null){instance = new Singleton_6();}}}return instance;}}
优点:线程安全,不会和上一种出现两个对象。
缺点:无
7.内部类的实现方式
public class Singleton_7 {private Singleton_7(){}private static class InstanceHolder{static final Singleton_7 INSTANCE = new Singleton_7();}public static Singleton_7 getInstance(){return InstanceHolder.INSTANCE;}}
优点:直接从内部类中获取对象,与第一种写法类似
缺点:与第一种写法相比,不会出现浪费内存的现象,内部类默认是不加载的,什么时候用到,什么时候加载。
8.枚举方式
public enum Singleton_8 {INSTANCE;public Singleton_8 getInstance(){return INSTANCE;}}
优点:最完美,不仅可以解决线程同步,还可以防止反序列化,枚举类没有构造方法
缺点:无
