饿汉式
package singleton.hungry;
public class HungrySingleton {
public static HungrySingleton instance = new HungrySingleton();
}
懒汉式
package singleton.lazy;
public class LazySingleton {
// volatile避免指令重排,产生线程安全问题
private volatile static LazySingleton instance;
private static boolean initialized = false;
private LazySingleton() {
// 防止反射破坏单例
synchronized (LazySingleton.class) {
if (!initialized) {
initialized = true;
} else {
throw new RuntimeException("单例被破坏!");
}
}
}
/**
* 线程不安全
* @return
*/
public static LazySingleton getInstance1() {
if (null == instance) {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
instance = new LazySingleton();
}
return instance;
}
/**
* 线程安全,加锁存在效率问题
* @return
*/
public static synchronized LazySingleton getInstance2() {
if (null == instance) {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
instance = new LazySingleton();
}
return instance;
}
/**
* 双重校验锁
* @return
*/
public static LazySingleton getInstance3() {
if (null == instance) {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
synchronized (LazySingleton.class) {
if (null == instance) {
instance = new LazySingleton();
}
}
}
return instance;
}
}
静态内部类实现
package singleton.lazy;
public class StaticInnerClassSingleton {
private StaticInnerClassSingleton() {}
private static class singletonHolder {
private static final StaticInnerClassSingleton INSTANCE = new StaticInnerClassSingleton();
}
public static StaticInnerClassSingleton getMyInstance() {
return singletonHolder.INSTANCE;
}
}
注册登记式
package singleton.register;
import java.util.HashMap;
public class MapRegisterSingleton {
private static HashMap<String, Object> registerMap = new HashMap();
private MapRegisterSingleton() {
}
public static MapRegisterSingleton getMyInstance(String name) {
if (null == name) {
name = MapRegisterSingleton.class.getName();
}
if (null == registerMap.get(name)) {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
synchronized (MapRegisterSingleton.class) {
if (null == registerMap.get(name)) {
registerMap.put(name, new MapRegisterSingleton());
}
}
}
return (MapRegisterSingleton) registerMap.get(name);
}
}
枚举
package singleton.register;
public enum EnumRegisterSingleton {
INSTANCE;
}
序列化/反序列化
package singleton.serialize;
import java.io.Serializable;
public class SerializeSingleton implements Serializable {
private static final SerializeSingleton INSTANCE = new SerializeSingleton();
private SerializeSingleton() {
}
public static SerializeSingleton getMyInstance() {
return INSTANCE;
}
/**
* 保证单例
* @return
*/
private Object readResolve() {
return INSTANCE;
}
}
测试
package singleton.test;
import singleton.hungry.HungrySingleton;
import singleton.lazy.LazySingleton;
import singleton.lazy.StaticInnerClassSingleton;
import singleton.register.MapRegisterSingleton;
import singleton.serialize.SerializeSingleton;
import java.io.*;
import java.lang.reflect.Constructor;
public class test {
public static void main(String[] args) {
for (int i = 0; i < 100; i++) {
// new Thread(() -> testHungrySingleton()).start();
new Thread(() -> testLazySingleton()).start();
// new Thread(() -> testStaticInnerClassSingleton()).start();
// new Thread(() -> testMapRegisterSingleton()).start();
}
// testSerializeSingleton();
}
public static void testHungrySingleton() {
System.out.println(HungrySingleton.instance);
}
public static void testLazySingleton() {
System.out.println(LazySingleton.getInstance1());
// System.out.println(LazySingleton.getInstance2());
// System.out.println(LazySingleton.getInstance3());
// 反射破坏单例
// Class<LazySingleton> clazz = LazySingleton.class;
// Constructor<?>[] constructors = clazz.getDeclaredConstructors();
// for (int i = 0; i < constructors.length; i++) {
// Constructor<?> constructor = constructors[i];
// constructor.setAccessible(true);
// try {
// Object o = constructor.newInstance();
// System.out.println(o);
// } catch (Exception e) {
// e.printStackTrace();
// }
// }
}
public static void testStaticInnerClassSingleton() {
System.out.println(StaticInnerClassSingleton.getMyInstance());
}
public static void testMapRegisterSingleton() {
System.out.println(MapRegisterSingleton.getMyInstance("s"));
}
public static void testSerializeSingleton() {
SerializeSingleton s1;
SerializeSingleton s2 = SerializeSingleton.getMyInstance();
try {
FileOutputStream fos = new FileOutputStream("testSerializeSingleton.obj");
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(s2);
oos.flush();
oos.close();
FileInputStream fis = new FileInputStream("testSerializeSingleton.obj");
ObjectInputStream osi = new ObjectInputStream(fis);
s1 = (SerializeSingleton) osi.readObject();
osi.close();
System.out.println(s1);
System.out.println(s2);
System.out.println(s1 == s2);
} catch (Exception e) {
e.printStackTrace();
}
}
}