目录
一、定义一个容器单例
- 一、定义一个容器单例
- 二、多线程测试容器单例:
- 三、结论
package com.rf.designPatterns.singleton.containerSingleton;
import org.apache.commons.lang.StringUtils;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/**
* @description: 容器单例
* @author: xiaozhi
* @create: 2020-06-05 08:46
*/
public class ContainerSingleton {
/**
* @Description: 使用HashMap,如果采用多线程测试,是线程不安全的;
* 使用Hashtable,如果采用多线程测试,是线程安全的,但是影响性能。
* 使用ConcurrentHashMap,如果采用多线程测试,在本示例中ConcurrentHashMap是静态的,并且操作了该map,这种情况并不是绝对的线程安全
* @Author: xz
* @Date: 2020/6/5 10:35
*/
private static Map singletonMap =new HashMap();
//构造器
private ContainerSingleton(){
}
/**
* @Description: 存放多个实例的方法
* @Param: [key, instance]
* @Author: xz
* @return: void
* @Date: 2020/6/5 9:05
*/
public static void putInstance(String key,Object instance){
//判断key不为空字符串并且实例不为null
if(StringUtils.isNotBlank(key) && instance!=null){
//判断key不在声明的singletonMap中
if(!singletonMap.containsKey(key)){
//存储key和实例到singletonMap
singletonMap.put(key,instance);
}
}
}
/**
* @Description: 通过key获取singletonMap中的Object
* @Param:
* @Author: xz
* @return:
* @Date: 2020/6/5 9:08
*/
public static Object getInstance(String key){
return singletonMap.get(key);
}
}
二、多线程测试容器单例:
1、定义一个线程类
package com.rf.designPatterns.singleton.containerSingleton;
/**
* @description:
* @author: xiaozhi
* @create: 2020-06-05 10:19
*/
public class MyThread implements Runnable{
@Override
public void run() {
ContainerSingleton.putInstance("objectKey",new Object());
Object instance = ContainerSingleton.getInstance("objectKey");
System.out.println(Thread.currentThread().getName()+": "+instance);
}
}
2、定义一个测试类
package com.rf.designPatterns.singleton.containerSingleton;
/**
* @description:
* @author: xiaozhi
* @create: 2020-06-05 10:22
*/
public class Test {
public static void main(String[] args) {
Thread thread1 = new Thread(new MyThread());
Thread thread2 = new Thread(new MyThread());
thread1.start();
thread2.start();
}
}
3、多线程debug启动,thread-0和thread-1创建的对象不是同一对象,并且key是相同的 4、输出结果相同,如下图:(获取的是同一对象的原因:是因为容器单例中使用了HashMap,其中key是相同的)
- 使用HashMap,如果采用多线程测试,是线程不安全的;
- 使用Hashtable,如果采用多线程测试,是线程安全的,但是影响性能。
- 使用ConcurrentHashMap,如果采用多线程测试,在本示例中ConcurrentHashMap是静态的,并且操作了该map,这种情况并不是绝对的线程安全