小故事: 单例是什么意思呢?大家可以理解为一朝天子一朝臣;在历史的发展中,一个朝代只有一个皇帝,皇帝不死太子就没办法继位,皇帝更换一般都跟随着元号的改变;在一个朝代中,每次大臣上朝拜见的都是同一个皇帝,如果每天见到的皇帝不一样,肯定会出乱子的,不过想想还是挺赤鸡的!废话不多说,上代码:
单例构建方式
1:饿汉式
类加载到内存后,就实例化一个单例,JVM保证线程安全
优点:简单实用(推荐使用)
缺点:不管用到与否,类装载时就会完成实例化
public class Singleton01{
private static final Singleton01 INSTANCE = new Singleton01();
private Singleton01() {};
public static Singleton01 getInstance() {
return INSTANCE;
}
}
public class Singleton02 {
private static final Singleton02 INSTANCE;
static {
INSTANCE = new Singleton02();
}
private Singleton02() {};
public static Singleton02 getInstance() {
return INSTANCE;
}
}
2:懒汉式
线程不安全的实现方式;多线程访问可能会出现多个实例
public class Singleton03 {
private static Singleton03 INSTANCE;
private Singleton03() {}
public static Singleton03 getInstance() {
if (INSTANCE == null) {
INSTANCE = new Singleton03();
}
return INSTANCE;
}
}
线程安全的实现方式一:性能较低
public class Singleton04 {
private static Singleton04 INSTANCE;
private Singleton04() {
}
public static synchronized Singleton04 getInstance() {
if (INSTANCE == null) {
INSTANCE = new Singleton04();
}
return INSTANCE;
}
}
双检锁:降低锁的粒度,可以提升性能,但是相对饿汉式性能仍然比较低
public class Singleton05 {
private static Singleton05 INSTANCE;
private Singleton05() {
}
public static Singleton05 getInstance() {
if (INSTANCE == null) {
//双重检查(有必要),可以通过双重检查减少很多不必要的锁争抢
synchronized (Singleton05.class) {
if(INSTANCE == null) {
INSTANCE = new Singleton05();
}
}
}
return INSTANCE;
}
}
3:静态内部类方式
JVM保证单例;
加载外部类时不会加载内部类,这样可以实现懒加载
public class Singleton06 {
private Singleton06() {}
private static class Singleton06Holder {
private final static Singleton06 INSTANCE = new Singleton06();
}
public static Singleton06 getInstance() {
return Singleton06Holder.INSTANCE;
}
}
注意:以上所有方式可以实现单例,但是不能防止反序列化
4:枚举方式
不仅可以解决线程同步,还可以防止反序列化;最简单省事的方法
public enum Singleton07 {
INSTANCE;
}
967

被折叠的 条评论
为什么被折叠?



