我们耳熟能详的单例有懒汉式、饿汉式等
例如下面这段的饿汉式
用private修饰构造方法,防止外界通过无参的构造方法直接创建对象,但是这样还是可以通过反射来攻击,造成代码的不安全,可以考虑设定一个变量,在创建第二个对象的时候抛出一个自定义的异常。
这样就安全了吗?
如果我将这个对象序列化到本地,然后再反序列化回来,这个对象还是原来的对象吗?不是的,这时可以考虑使用序列化的hock函数readResolve()来解决,当反序列化时,就会自动调用这个 readResolve方法来返回我们指定好的对象,如下图
还有一种非常简洁的方式,通过枚举实现单例
Single就是要实现单例的类,通过SingeltonEnum.INSTANCE.getInstance()创建单例对象,枚举实际上是一种语法糖,反编译后会发现是由静态方法和匿名内部类组成。
总结:单例的实现有很多种,还有double-check,同步方法等方式实现,在这里不一一赘述,在effective java中作者强烈推荐枚举来实现高效安全的单例,不会被反射和序列化攻击所困扰。