亚洲激情专区-91九色丨porny丨老师-久久久久久久女国产乱让韩-国产精品午夜小视频观看

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》
  • 首頁 > 
  • 教程 > 
  • 開發技術 > 
  • Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題

Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題

發布時間:2022-03-04 13:49:30 來源:億速云 閱讀:136 作者:小新 欄目:開發技術

這篇文章主要為大家展示了“Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題”,內容簡而易懂,條理清晰,希望能夠幫助大家解決疑惑,下面讓小編帶領大家一起研究并學習一下“Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題”這篇文章吧。

1.ArrayList的線程不安全解決方案

將main方法的第一行注釋打開,多執行幾次,會看到如下圖這樣的異常信息:???

Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題

這是一個 并發修改 異常,首先ArrayList肯定是線程不安全的,產生這個異常的原因就是可能第一個線程剛進入 ArrayList 集合中要進行 add 操作時,另外一個線程此時也進來進行 add 操作,而第三個線程又進來進行 get 操作,導致讀寫沒辦法進行同步了,最終打印結果的時候就炸了。

解決方案看代碼中的剩下幾行注釋。

package test.notsafe;
 
import java.util.*;
import java.util.concurrent.CopyOnWriteArrayList;
 
/**
 * 演示ArrayList的線程不安全問題及解決方案
 */
public class ThreadDemo2 {
    public static void main(String[] args) {
        //List<String> list = new ArrayList<>();
 
        //解決方法1:使用Vector
        //List<String> list = new Vector<>();
 
        //解決方法2:Collections
        //List<String> list = Collections.synchronizedList(new ArrayList<>());
 
        //解決方法3:CopyOnWriteArrayList
        List<String> list = new CopyOnWriteArrayList<>();
 
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
                list.add(UUID.randomUUID().toString().substring(0,8));
                System.out.println(list);
            },String.valueOf(i)).start();
        }
    }
}

Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題

關于 CopyOnWriteArrayList 解決線程不安全問題的簡單解釋:就看源碼中的 add(E e) 這個方法:

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();
        }
    }

這個 CopyOnWriteArrayList 在進行 add 添加操作之前,先進行 lock 上鎖,然后通過 getArray() 獲取到原 ArrayList 集合容器,之后調用 Arrays.copyOf 方法將原容器拷貝出一個新容器,因為要添加(長度自然也要 +1),之后向這個新容器中添加元素,添加完成之后,調用 setArray 方法將原容器的引用指向了這個新的容器。 那么這樣做的好處就是:添加元素在新容器中,原容器該是啥樣還是啥樣,其他線程要get讀取元素就還從原容器中讀(即多個線程可以進行并發讀);而其他線程要 add 添加,要等待其他線程完成之后,將原容器的引用指向新容器就可以了。

CopyOnWrite 容器在面對讀和寫的時候是兩個不同的容器,也是用到了讀寫分離的思想。

2.HashSet的線程不安全解決方案

這里如果是 new HashSet 了話,仍然可能出現向上面 ArrayList 一樣的 并發修改異常。解決方案看代碼中的注釋。

package test.notsafe;
 
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.UUID;
import java.util.concurrent.CopyOnWriteArraySet;
 
/**
 * 演示HashSet的線程不安全問題及解決方案
 */
public class ThreadDemo3 {
    public static void main(String[] args) {
        //Set<String> set = new HashSet<>();
 
        //解決方法1:Collections
        //Set<String> set = Collections.synchronizedSet(new HashSet<>());
 
        //解決方法2:CopyOnWriteArraySet
        Set<String> set = new CopyOnWriteArraySet<>();
 
        for (int i = 0; i < 20; i++) {
            new Thread(() -> {
                set.add(UUID.randomUUID().toString().substring(0,8));
                System.out.println(set);
            },String.valueOf(i)).start();
        }
    }
}

3.HashMap的線程不安全解決方案

package test.notsafe;
 
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap;
 
/**
 * 演示HashMap的線程不安全問題及解決方案
 */
public class ThreadDemo4 {
    public static void main(String[] args) {
        //Map<String,Object> map = new HashMap<>();
 
        //解決方法1:Collections
        //Map<String,Object> map = Collections.synchronizedMap(new HashMap<>());
 
        //解決方法2:ConcurrentHashMap
        Map<String,Object> map = new ConcurrentHashMap<>();
 
        for (int i = 0; i < 10; i++) {
            String key = String.valueOf(i);
            new Thread(() -> {
                map.put(key,UUID.randomUUID().toString().substring(0,8));
                System.out.println(map);
            },String.valueOf(i)).start();
        }
    }
}

以上是“Java多線程高并發中如何解決ArrayList與HashSet和HashMap不安全的問題”這篇文章的所有內容,感謝各位的閱讀!相信大家都有了一定的了解,希望分享的內容對大家有所幫助,如果還想學習更多知識,歡迎關注億速云行業資訊頻道!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

来安县| 鄂托克旗| 开封市| 九台市| 涪陵区| 陆良县| 彭泽县| 鄂托克旗| 藁城市| 墨竹工卡县| 随州市| 双江| 谷城县| 镇巴县| 福鼎市| 六枝特区| 扎赉特旗| 扬州市| 琼海市| 汉沽区| 玛纳斯县| 开化县| 九龙县| 尼木县| 吐鲁番市| 阿坝县| 偃师市| 宜章县| 洪江市| 台湾省| 长子县| 泸州市| 松溪县| 武安市| 屏山县| 连城县| 华宁县| 鞍山市| 和平县| 阜康市| 芜湖县|