单例模式:
一. 定义:
(1)、在任何情况下,单例类永远只有一个实例存在
(2)、单例需要有能力为整个系统提供这一唯一实例
二. 实现
2.1饿汉式单例
package org.mlinge.s01;
public class MySingleton {
private static MySingleton instance = new MySingleton();
private MySingleton(){
//防止其他通过反射调用构造方法,破解单例
if (instance != null) {
throw new RuntimeException();
}
}
public static MySingleton getInstance() {
return instance;
}
}
优点:1.实例的初始化由JVM装载类的时候进行,保证了线程的安全性 2.实现简单方便 3.实例的访问效率高
缺点: 不能实现懒加载,如果不调用getInstance(),那么这个类就白白的占据内存,资源的利用率不高
2.2懒汉式单例(效率低)
public class MySingleton {
private static MySingleton instance = null;
private MySingleton(){}
public synchronized static MySingleton getInstance() {
try {
if(instance != null){//懒汉式
}else{
//创建实例之前可能会有一些准备性的耗时工作
Thread.sleep(300);
instance = new MySingleton();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
return instance;
}
}
2.3同步代码块实现单例(效率低)
public class MySingleton {
private static MySingleton instance = null;
private MySingleton(){}
//public synchronized static MySingleton getInstance() {
public static MySingleton getInstance() {
try {
synchronized (MySingleton.class) {
if(instance != null){//懒汉式
}else{
//创建实例之前可能会有一些准备性的耗时工作
Thread.sleep(300);
instance = new MySingleton();
}
}
} catch (InterruptedException e) {
e.printStackTrace();
}
return instance;
}
}
2.4 Double Check Locking 双检查锁机制(推荐)
package org.mlinge.s05;
public class MySingleton {
//使用volatile关键字保其可见性
volatile private static MySingleton instance = null;
private MySingleton(){}
public static MySingleton getInstance() {
try {
if(instance != null){//懒汉式
}else{
//创建实例之前可能会有一些准备性的耗时工作
Thread.sleep(300);
synchronized (MySingleton.class) {
if(instance == null){//二次检查
instance = new MySingleton();
}
}
}
} catch (InterruptedException e) {
e.printStackTrace();
}
return instance;
}
2.5使用静态内置类实现单例模式(推荐)
package org.mlinge.s06;
public class MySingleton {
//内部类
private static class MySingletonHandler{
private static MySingleton instance = new MySingleton();
}
private MySingleton(){}
public static MySingleton getInstance() {
return MySingletonHandler.instance;
}
2.6 序列化与反序列化的单例模式实现
package org.mlinge.s07;
import java.io.ObjectStreamException;
import java.io.Serializable;
public class MySingleton implements Serializable {
private static final long serialVersionUID = 1L;
//内部类
private static class MySingletonHandler{
private static MySingleton instance = new MySingleton();
}
private MySingleton(){}
public static MySingleton getInstance() {
return MySingletonHandler.instance;
}
//该方法在反序列化时会被调用,该方法不是接口定义的方法,有点儿约定俗成的感觉
protected Object readResolve() throws ObjectStreamException {
System.out.println("调用了readResolve方法!");
return MySingletonHandler.instance;
}
}
2.7 静态代码块
package org.mlinge.s08;
public class MySingleton{
private static MySingleton instance = null;
private MySingleton(){}
static{
instance = new MySingleton();
}
public static MySingleton getInstance() {
return instance;
}
}
2.8 枚举内部类实现单例
package org.mlinge.s10;
public class ClassFactory{
private enum MyEnumSingleton{
singletonFactory;
private MySingleton instance;
private MyEnumSingleton(){//枚举类的构造方法在类加载是被实例化
instance = new MySingleton();
}
public MySingleton getInstance(){
return instance;
}
}
public static MySingleton getInstance(){
return MyEnumSingleton.singletonFactory.getInstance();
}
}
class MySingleton{//需要获实现单例的类,比如数据库连接Connection
public MySingleton(){}
}
三. 单例模式测试
@Test
public void test2(){
LinkedHashSet<String> integers = new LinkedHashSet<>();
for (int i = 0; i < 100; i++) {
new Thread(()->{
integers.add(String.valueOf(MySingleton.getInstance()));
}).run();
}
System.out.println(integers.size());
}
本文详细介绍了Java中实现单例模式的六种方法,包括饿汉式、懒汉式、同步代码块、双检查锁机制、静态内部类和枚举内部类。其中,双检查锁机制和静态内部类实现被推荐使用。

354

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



