多线程下如何操作ArrayList,Set

//不安全的写法 ,会报出 ConcurrentModificationException,当方法检测到对象的并发修改,但不允许这种修改时,抛出此异常。
public static void main(String[] args) { List<String> list = new ArrayList(); for (int i = 0;i<10;i++){ new Thread(()->{ list.add(UUID.randomUUID().toString().substring(0,5)); System.out.println(list); }).start(); } }

改进方法1:用vector,核心用了synchronized

  List<String> list = new Vector<>();

改进方法2:用Collections工具类下的方法,核心用了synchronized

   List<String> list = Collections.synchronizedList(new ArrayList<>());

改进方法3:用JUC下面的 CopyOnWriteArrayList,写入时复制,

        List<String> list = new CopyOnWriteArrayList<>();

//写入时复制的核心。复制一份 
public boolean add(E e) {
        final ReentrantLock lock = this.lock;
        lock.lock();
        try {
            Object[] elements = getArray();
            int len = elements.length;
            Object[] newElements = Arrays.copyOf(elements, len + 1);
            newElements[len] = e;
            setArray(newElements);
            return true;
        } finally {
            lock.unlock();
        }
    }

 

二、Set  

 类似的安全操作

Set<String> set = Collections.synchronizedSet(new HashSet<>());
Set<String> set = new CopyOnWriteArraySet<>();

//hashSet底层是HashMap
public HashSet() { map = new HashMap<>(); }
 public boolean add(E e) {
return map.put(e, PRESENT)==null;
}
 

 




posted @ 2021-11-16 23:07  阿·超  阅读(226)  评论(0)    收藏  举报