CopyOnWriteArraySet

CopyOnWriteArraySet

  • Set不安全

    • 多条线程执行set添加方法

      //java.util.ConcurrentModificationException 并发修改异常
      public class Test04 {
          public static void main(String[] args) {
              Set<String> set = new HashSet<>();
              for (int i = 0; i < 30; i++) {
                  new Thread(()->{
                      set.add(UUID.randomUUID().toString().substring(0,5));
                      System.out.println(set);
                  },String.valueOf(i)).start();
              }
          }
      }
      //Exception in thread "6" Exception in thread "7" Exception in thread "3" Exception in thread "18" Exception in thread "23" Exception in thread "25" java.util.ConcurrentModificationException
      	at java.util.HashMap$HashIterator.nextNode(HashMap.java:1429)
      	at java.util.HashMap$KeyIterator.next(HashMap.java:1453)
      	at java.util.AbstractCollection.toString(AbstractCollection.java:461)
      	at java.lang.String.valueOf(String.java:2981)
      	at java.io.PrintStream.println(PrintStream.java:821)
      	at com.saxon.demo.Test04.lambda$main$0(Test04.java:11)
      

    解决方案

    1. 使用Collections下的Collections.synchronizedSet(new HashSet<>()); 方法创建Set集合
    2. 使用JUC下的CopyOnWriteArraySet方法
    //java.util.ConcurrentModificationException 并发修改异常
    public class Test04 {
        public static void main(String[] args) {
            // Set<String> set = new HashSet<>();
            /*解决方案
             * 1. Set<String> set=Collections.synchronizedSet(new HashSet<>());
             * 2. Set<String> set=new CopyOnWriteArraySet<>();*/
           // Set<String> set = Collections.synchronizedSet(new HashSet<>());
            Set<String> set=new CopyOnWriteArraySet<>();
            for (int i = 0; i < 30; i++) {
                new Thread(()->{
                    set.add(UUID.randomUUID().toString().substring(0,5));
                    System.out.println(set);
                },String.valueOf(i)).start();
            }
        }
    }
    

HashSet底层是什么?

HashSet底层就是HashMap的底层实现原理,就只是加了个key不能被重复

public HashSet() {
    map = new HashMap<>();
}
// add: set本质就是 map 中 key是无法重复的!
public boolean add(E e) {
        return map.put(e, PRESENT)==null;
    }

PRESENT :private static final Object PRESENT = new Object();//常量
上一篇:深度解析HashSet.add执行过程


下一篇:02MyBatis基本运行环境