1 单例模式
单例模式指的是一个类仅有一个实例,并提供一个访问它的全局访问点。
它的类图为
2 创建方式
2.1 饿汉式
package DesignPatterns;
public class Singleton2 {
// 饿汉式
private static Singleton2 instance = new Singleton2();
private Singleton2() {
}
public static Singleton2 getInstance() {
return instance;
}
}
简单粗暴,类加载的时候就会初始化对象,会造资源浪费,线程安全。
2.2 懒汉式
package DesignPatterns;
public class Singleton1 {
// 懒汉式
private static Singleton1 instance = null;
private Singleton1() {
}
public static Singleton1 getInstance() {
if (instance == null) {
instance = new Singleton1();
}
return instance;
}
}
具有延迟加载的好处,但是线程不安全2.3 懒汉式,线程安全
package DesignPatterns;
public class Singleton3 {
// 懒汉式,线程安全
private static Singleton3 instance = null;
private Singleton3() {
}
public static synchronized Singleton3 getInstance() {
if (instance == null) {
instance = new Singleton3();
}
return instance;
}
}
线程安全,使用了同步会造成效率降低,因为对象只需要初始化一次,之后无需初始化,也就不需要同步2.4 懒汉式,双重检验锁
package DesignPatterns;
public class Singleton4 {
// 懒汉式,双重检验锁
private static Singleton4 instance = null;
private Singleton4() {
}
public static Singleton4 getInstance() {
if (instance == null) {
synchronized (Singleton4.class) {
if (instance == null) {
instance = new Singleton4();
}
}
}
return instance;
}
}
大大减少了不需要同步的时机,第二个判空的原因:在对象为空的时候,存在多个线程要初始化的情况,只有先获得锁的线程才可以实例化一个对象,其他竞争的线程不能再实例一个对象。2.5 静态内部类
package DesignPatterns;
public class Singleton5 {
// 静态内部类
private Singleton5() {
}
private static class SingletonHolder{
private static Singleton5 instance = new Singleton5();
}
public static Singleton5 getInstance() {
return SingletonHolder.instance;
}
}
由于类的加载机制,静态属性只会被加载一次,使用内部类到达了延迟实例化对象的效果。