參考資料:html
https://stackoverflow.com/questions/35534906/java-hashmap-getobject-infinite-loopshell
Map的一些實現類有及其特性安全
類多線程 |
線程安全 | 特性 |
Hashtableide |
是 | Key不能爲null |
HashMapoop |
否 | 讀寫效率最高,但在Java6多線程環境下使用不當可能陷入死循環,進而致使CPU使用率太高(原理可參見:http://coolshell.cn/articles/9606.html) |
Collections.synchronizedMap測試 |
是 | Collections.SynchronizedMap在Map全部方法基礎上加鎖,效率與HashTable至關 |
ConcurrentHashMapspa |
是 | 採用分段鎖,get通常不加鎖,put分段鎖,key/value不能爲null,效率僅次於HashMap |
如下代碼測試各種的讀寫效率線程
import java.util.Collections; import java.util.HashMap; import java.util.Hashtable; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.TimeUnit; /** * @Description: 測試map */ public class ThreadMapTest { public static void main(String[] args) throws InterruptedException { Map<Integer, Integer> hashtable = new Hashtable<>(); Map<Integer, Integer> hashmap = new HashMap<>(); Map<Integer, Integer> synchronizedHashMap = Collections.synchronizedMap(new HashMap<>()); Map<Integer, Integer> concurrentHashMap = new ConcurrentHashMap<>(); test(hashtable); test(hashmap); test(synchronizedHashMap); test(concurrentHashMap); } private static void test(Map<Integer, Integer> map) throws InterruptedException { int testTimes = 5; long totalTimeMillis = 0; for (int k = 0; k < testTimes; k++) { totalTimeMillis += costTimeMillis(map); } System.out.println("Test " + map.getClass() + " average time " + (totalTimeMillis / testTimes)); } private static long costTimeMillis(Map<Integer, Integer> map) throws InterruptedException { int count = 5; ExecutorService executorService = Executors.newFixedThreadPool(count); long startMillis = System.currentTimeMillis(); for (int i = 0; i < count; i++) { executorService.execute(new Runnable() { @Override public void run() { for (int j = 0; j < 500000; j++) { map.put(0, 0); map.get(0); } } }); } executorService.shutdown(); executorService.awaitTermination(Long.MAX_VALUE, TimeUnit.DAYS); return System.currentTimeMillis() - startMillis; } }
輸出結果以下:
Test class java.util.Hashtable average time 267 Test class java.util.HashMap average time 67 Test class java.util.Collections$SynchronizedMap average time 262 Test class java.util.concurrent.ConcurrentHashMap average time 167