单例模式
保证只有一个实例
定义私有的构造器
定义对外的方法创建
1、饿汉式
在类加载中就创建了对象
缺点:可能会永远用不到,浪费空间。对资源的利用不好。
public class Singleton {
// 在类加载时就创建实例
private static final Singleton instance = new Singleton();
// 私有构造方法,防止外部实例化
private Singleton() {
}
// 全局访问点
public static Singleton getInstance() {
return instance;
}
}
2、懒汉式
用的时候才创建。
可以先声明为空,做if判断后没有对象再创建一个。
public class Singleton {
// 使用 volatile 保证多线程环境下的可见性和防止指令重排序
private static volatile Singleton instance;
private Singleton() {
}
// 双重检查锁定
public static Singleton getInstance() {
if (instance == null) {
synchronized (Singleton.class) {
if (instance == null) {
instance = new Singleton();
}
}
}
return instance;
}
}
但是懒汉式不能解决多线程的问题
所以就出现了双重检测锁
同时,需要在上面声明的instance加上volatile关键字修饰
保证分配空间、成功创建对象并赋值给instance;线程的可见性
此时外部可以通过反射暴力破解
可以在构造方法上加判断,抛异常,中止行为
但是此时还可以用序列化和反序列化的方式破解
这种方式创建对象是和原来的instance是不同的,违背了单例
可以重写readReslove方法
return instance;这样就前后两个对象都相同了。
应用
工厂、bean、池