设计一个类,只能产生该类的一个实例。
方法一:懒汉式,线程不安全
package com.pattern.singleton;
public class Singleton1 {
// private static boolean isCreated = false;
private static Singleton1 instance = null;
private Singleton1() {}
public static Singleton1 getInstance() {
if(instance == null) {
instance = new Singleton1();
}
return instance;
}
}
上述代码只能确保在单线程情况下满足要求,在多线程方式下可能出错!
方法二:懒汉式,线程安全,多线程环境下效率不高
使用synchronized关键字进行同步:
public synchronized static Singleton1 getInstance() {
if(instance == null) {
instance = new Singleton1();
}
return instance;
}
package com.pattern.singleton;
public class Singleton1 {
// private static boolean isCreated = false;
private static Object syncObj = new Object();
private static Singleton1 instance = null;
private Singleton1() {}
public static Singleton1 getInstance() {
synchronized(syncObj) {
if(instance == null) {
instance = new Singleton1();
}
}
return instance;
}
}
我们只需要在还没有创建实例的时候才会进行同步锁,以保证只有一个线程去创建实例。而当实例已经创建成果后,就没必要进行加锁的操作了。比上述方法效率更高,改进后的代码如下:
方法三:使用双重校验锁,线程安全【推荐】
package com.pattern.singleton;
public class Singleton1 {
// private static boolean isCreated = false;
private static Object syncObj = new Object();
private static Singleton1 instance = null;
private Singleton1() {}
public static Singleton1 getInstance() {
if(instance == null) {
synchronized(syncObj) {
if(instance == null) {
instance = new Singleton1();
}
}
}
return instance;
}
}
方法四:饿汉式,线程安全
package com.pattern.singleton;
public class Singleton1 {
private static Singleton1 instance = new Singleton1();
// static {
// instance = new Singleton1();
// }
private Singleton1() {}
public static Singleton1 getInstance() {
return instance;
}
}
该方法存在一个问题:就是会有过早创建实例的问题!降低了内存的使用效率!
方法五:使用静态内部类,线程安全【推荐】
package com.pattern.singleton;
public class Singleton1 {
private Singleton1() {}
public static Singleton1 getInstance() {
return Nested.instance;
}
private static class Nested {
private Nested() {}
private static final Singleton1 instance = new Singleton1();
}
}