<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??碼云GVP開源項目 12k star Uniapp+ElementUI 功能強大 支持多語言、二開方便! 廣告
                [java.util.concurrent 之ConcurrentHashMap 源碼分析](http://www.iteye.com/topic/977348) 最近有點想研究下java.util.concurrent 包下的一些類中的實現,在現實中也對這包里的類應用不少,但都沒怎么去深入理解,只是聽說里面的實現在高并發中有不錯的性能。。接下將對里面的幾個比較常用的類的源碼進行分析。。 ???**ConcurrentHashMap類** ?? 研究源碼時,我一般喜歡從實際的應用中去一步步調試分析。。這樣理解起來容易很多。 ??**?實際應用:** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. ?ConcurrentMap?map?=?new?ConcurrentHashMap();?? 2. String?oldValue?=?map.put("zhxing",?"value");?? 3. String?oldValue1?=?map.put("zhxing",?"value1");?? 4. String?oldValue2?=?map.putIfAbsent("zhxing",?"value2");?? 5. String?value?=?map.get("zhxing");?? 6. ?? 7. System.out.println("oldValue:"?+?oldValue);?? 8. System.out.println("oldValue1:"?+?oldValue1);?? 9. System.out.println("oldValue2:"?+?oldValue2);?? 10. System.out.println("value:"?+?value);?? ? 輸出結果: Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. oldValue:null?? 2. oldValue1:value?? 3. oldValue2:value1?? 4. value:value1?? ? **先從new 方法開始** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. ????/**? 2. ?????*?Creates?a?new,?empty?map?with?a?default?initial?capacity?(16),?load? 3. ?????*?factor?(0.75)?and?concurrencyLevel(也就是鎖的個數)?(16).? 4. ?????*?? 5. ?????*/?? 6. public?ConcurrentHashMap()?{?? 7. ????????this(DEFAULT_INITIAL_CAPACITY,?DEFAULT_LOAD_FACTOR,?DEFAULT_CONCURRENCY_LEVEL);?? 8. ????}?? 9. //?當都是默認的設置參數?? 10. ????public?ConcurrentHashMap(int?initialCapacity,?float?loadFactor,?? 11. ????????????int?concurrencyLevel)?{?? 12. ????????if?(!(loadFactor?>?0)?||?initialCapacity?0?||?concurrencyLevel?0)?? 13. ????????????throw?new?IllegalArgumentException();?? 14. ????????//?MAX_SEGMENTS?=?1??? 15. ????????if?(concurrencyLevel?>?MAX_SEGMENTS)?? 16. ????????????concurrencyLevel?=?MAX_SEGMENTS;?? 17. ?? 18. ????????//?Find?power-of-two?sizes?best?matching?arguments?? 19. ????????//?這里是根據設定的并發數查找最優的并發數?? 20. ????????int?sshift?=?0;?? 21. ????????int?ssize?=?1;?? 22. ????????while?(ssize? 23. ????????????++sshift;?? 24. ????????????ssize?1;//?不斷右移?? 25. ????????}?? 26. ????????//?到這里,sshift=4,ssize=16.因為concurrencyLevel=16=1?? 27. ????????segmentShift?=?32?-?sshift;//?=16?? 28. ????????segmentMask?=?ssize?-?1;//?=3?? 29. ????????//?創建了16個分段(Segment),其實每個分段相當于一個帶鎖的map?? 30. ????????this.segments?=?Segment.newArray(ssize);?? 31. ?? 32. ????????if?(initialCapacity?>?MAXIMUM_CAPACITY)?? 33. ????????????initialCapacity?=?MAXIMUM_CAPACITY;?? 34. ????????//?這里是計算每個分段存儲的容量?? 35. ????????int?c?=?initialCapacity?/?ssize;//?c=16/16=1?? 36. ????????if?(c?*?ssize?//?防止分段的相加的容量小于總容量?? 37. ????????????++c;?? 38. ????????int?cap?=?1;?? 39. ????????//?如果初始容量比cap的容量小,則已雙倍的容量增加?? 40. ????????while?(cap? 41. ????????????cap?1;?? 42. ????????//?分別new分段?? 43. ????????for?(int?i?=?0;?i?this.segments.length;?++i)?? 44. ????????????this.segments[i]?=?new?Segment(cap,?loadFactor);?? 45. ????}?? ? 這里提到了一個Segment 這個類,其實這個是總map 的分段,就是為了實現分段鎖機制。 Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. /**? 2. ?????*?Segments?are?specialized?versions?of?hash?tables.?This?subclasses?from? 3. ?????*?ReentrantLock?opportunistically,?just?to?simplify?some?locking?and?avoid? 4. ?????*?separate?construction.?map?的分段實現,擴展了鎖機制? 5. ?????*/?? 6. ????static?final?class?Segment?extends?ReentrantLock?implements?? 7. ????????????Serializable?{?? 8. //。。。?? 9. Segment(int?initialCapacity,?float?lf)?{?? 10. ????????????loadFactor?=?lf;?? 11. ????????????//?這個是開始初始化map容器了?? 12. ????????????setTable(HashEntry.?newArray(initialCapacity));?? 13. ????????}?? 14. ????????/**? 15. ?????????*?Sets?table?to?new?HashEntry?array.?Call?only?while?holding?lock?or?in? 16. ?????????*?constructor.? 17. ?????????*/?? 18. ????????void?setTable(HashEntry[]?newTable)?{?? 19. ????????????threshold?=?(int)?(newTable.length?*?loadFactor);?? 20. ????????????table?=?newTable;?? 21. ????????}?? 22. }?? 23. ?? 24. ????//?這個是實際保存到map的東西了,如果對HashMap源碼有了解的話,是不是覺得很像Hash.Entry,但又沒實現Map.Entry接口,它是用另外個類WriteThroughEntry?? 25. ????//?來實現這個Map.Entry接口的。?? 26. ????static?final?class?HashEntry?{?? 27. ????????final?K?key;?? 28. ????????final?int?hash;?? 29. ????????volatile?V?value;?? 30. ????????final?HashEntry?next;?? 31. ?? 32. ????????HashEntry(K?key,?int?hash,?HashEntry?next,?V?value)?{?? 33. ????????????this.key?=?key;?? 34. ????????????this.hash?=?hash;?? 35. ????????????this.next?=?next;?? 36. ????????????this.value?=?value;?? 37. ????????}?? 38. ?? 39. ????????@SuppressWarnings("unchecked")?? 40. ????????//?新建數組,保存著map里的鍵值對?? 41. ????????static?final??HashEntry[]?newArray(int?i)?{?? 42. ????????????return?new?HashEntry[i];?? 43. ????????}?? ? **get方法實現** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. //ConcurrentHashMap類?????? 2. //?在這里發現,get操作幾乎是不帶鎖的。。效率提高很多?? 3. ????public?V?get(Object?key)?{?? 4. ????????//?key不能為null?。。?? 5. ????????int?hash?=?hash(key);?//?throws?NullPointerException?if?key?null?? 6. ????????return?segmentFor(hash).get(key,?hash);?? 7. ????}?? 8. ?? 9. ????//?這個hash方式不太懂,估計是為了能均勻分布吧?? 10. ????static?int?hash(Object?x)?{?? 11. ????????int?h?=?x.hashCode();?? 12. ????????h?+=?~(h?9);?? 13. ????????h?^=?(h?>>>?14);?? 14. ????????h?+=?(h?4);?? 15. ????????h?^=?(h?>>>?10);?? 16. ????????return?h;?? 17. ????}?? 18. ?? 19. ????/**? 20. ?????*?Returns?the?segment?that?should?be?used?for?key?with?given?hash?這個是尋找所在分段? 21. ?????*?? 22. ?????*?@param?hash? 23. ?????*????????????the?hash?code?for?the?key? 24. ?????*?@return?the?segment? 25. ?????*/?? 26. ????final?Segment?segmentFor(int?hash)?{?? 27. ????????//?hash>>>16&3?? 28. ????????return?segments[(hash?>>>?segmentShift)?&?segmentMask];?? 29. ????}?? 30. ?? 31. //Segment?類方法?? 32. ????????/*?Specialized?implementations?of?map?methods?*/?? 33. ????????//?獲得值了,和其他map的get的實現其實差不多?? 34. ????????V?get(Object?key,?int?hash)?{?? 35. ????????????//?count?是每個分段的鍵值對個數,而且是volatile,保證在內存中只有一份?? 36. ????????????if?(count?!=?0)?{?//?read-volatile?? 37. ????????????????//?獲得分段中hash鏈表的第一個值?? 38. ????????????????HashEntry?e?=?getFirst(hash);?? 39. ????????????????while?(e?!=?null)?{?? 40. ????????????????????if?(e.hash?==?hash?&&?key.equals(e.key))?{?? 41. ????????????????????????V?v?=?e.value;?? 42. ????????????????????????if?(v?!=?null)?? 43. ????????????????????????????return?v;?? 44. ????????????????????????//?這個做了一個挺有趣的檢查,如果v==null,而key!=null,的時候會等待鎖中value的值?? 45. ????????????????????????return?readValueUnderLock(e);?//?recheck?? 46. ????????????????????}?? 47. ????????????????????e?=?e.next;?? 48. ????????????????}?? 49. ????????????}?? 50. ????????????return?null;?? 51. ????????}?? 52. ?? 53. ????????/**? 54. ?????????*?Reads?value?field?of?an?entry?under?lock.?Called?if?value?field?ever? 55. ?????????*?appears?to?be?null.?This?is?possible?only?if?a?compiler?happens?to? 56. ?????????*?reorder?a?HashEntry?initialization?with?its?table?assignment,?which? 57. ?????????*?is?legal?under?memory?model?but?is?not?known?to?ever?occur.? 58. ?????????*/?? 59. ????????V?readValueUnderLock(HashEntry?e)?{?? 60. ????????????lock();?? 61. ????????????try?{?? 62. ????????????????return?e.value;?? 63. ????????????}?finally?{?? 64. ????????????????unlock();?? 65. ????????????}?? 66. ????????}?? **put 方法** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. //ConcurrentHashMap類?? 2. ????//?注意的是key?和value?都不能為空?? 3. ????public?V?put(K?key,?V?value)?{?? 4. ????????if?(value?==?null)?? 5. ????????????throw?new?NullPointerException();?? 6. ????????//?和get方式一樣的hash?方式?? 7. ????????int?hash?=?hash(key);?? 8. ????????return?segmentFor(hash).put(key,?hash,?value,?false);?? 9. ????}?? 10. ?? 11. //Segment?類?? 12. ?? 13. ????V?put(K?key,?int?hash,?V?value,?boolean?onlyIfAbsent)?{?? 14. ????????????//?這里加鎖了?? 15. ????????????lock();?? 16. ????????????try?{?? 17. ????????????????int?c?=?count;?? 18. ????????????????//?如果超過限制,就重新分配?? 19. ????????????????if?(c++?>?threshold)?//?ensure?capacity?? 20. ????????????????????rehash();?? 21. ????????????????HashEntry[]?tab?=?table;?? 22. ????????????????int?index?=?hash?&?(tab.length?-?1);?? 23. ????????????????HashEntry?first?=?tab[index];?? 24. ????????????????HashEntry?e?=?first;?? 25. ????????????????//?e的值總是在鏈表的最后一個?? 26. ????????????????while?(e?!=?null?&&?(e.hash?!=?hash?||?!key.equals(e.key)))?? 27. ????????????????????e?=?e.next;?? 28. ?? 29. ????????????????V?oldValue;?? 30. ????????????????if?(e?!=?null)?{?? 31. ????????????????????oldValue?=?e.value;?? 32. ????????????????????//?這里就是實現putIfAbsent?的方式?? 33. ????????????????????if?(!onlyIfAbsent)?? 34. ????????????????????????e.value?=?value;?? 35. ????????????????}?else?{?? 36. ????????????????????oldValue?=?null;?? 37. ????????????????????++modCount;?? 38. ????????????????????tab[index]?=?new?HashEntry(key,?hash,?first,?value);?? 39. ????????????????????count?=?c;?//?write-volatile?? 40. ????????????????}?? 41. ????????????????return?oldValue;?? 42. ????????????}?finally?{?? 43. ????????????????unlock();?? 44. ????????????}?? 45. ????????}?? 46. ?? 47. ????????//?這中擴容方式應該和其他map?的擴容一樣?? 48. ????????void?rehash()?{?? 49. ????????????HashEntry[]?oldTable?=?table;?? 50. ????????????int?oldCapacity?=?oldTable.length;?? 51. ????????????//?如果到了最大容量則不能再擴容了,max=1?? 52. ????????????if?(oldCapacity?>=?MAXIMUM_CAPACITY)?? 53. ????????????????return;?? 54. ?? 55. ????????????/*? 56. ?????????????*?Reclassify?nodes?in?each?list?to?new?Map.?Because?we?are?using? 57. ?????????????*?power-of-two?expansion,?the?elements?from?each?bin?must?either? 58. ?????????????*?stay?at?same?index,?or?move?with?a?power?of?two?offset.?We? 59. ?????????????*?eliminate?unnecessary?node?creation?by?catching?cases?where?old? 60. ?????????????*?nodes?can?be?reused?because?their?next?fields?won't?change.? 61. ?????????????*?Statistically,?at?the?default?threshold,?only?about?one-sixth?of? 62. ?????????????*?them?need?cloning?when?a?table?doubles.?The?nodes?they?replace? 63. ?????????????*?will?be?garbage?collectable?as?soon?as?they?are?no?longer? 64. ?????????????*?referenced?by?any?reader?thread?that?may?be?in?the?midst?of? 65. ?????????????*?traversing?table?right?now.? 66. ?????????????*/?? 67. ????????????//?以兩倍的方式增長?? 68. ????????????HashEntry[]?newTable?=?HashEntry.newArray(oldCapacity?1);?? 69. ????????????threshold?=?(int)?(newTable.length?*?loadFactor);?? 70. ????????????int?sizeMask?=?newTable.length?-?1;?? 71. ????????????//?下面的數據拷貝就沒多少好講的了?? 72. ????????????for?(int?i?=?0;?i? 73. ????????????????//?We?need?to?guarantee?that?any?existing?reads?of?old?Map?can?? 74. ????????????????//?proceed.?So?we?cannot?yet?null?out?each?bin.?? 75. ????????????????HashEntry?e?=?oldTable[i];?? 76. ?? 77. ????????????????if?(e?!=?null)?{?? 78. ????????????????????HashEntry?next?=?e.next;?? 79. ????????????????????int?idx?=?e.hash?&?sizeMask;?? 80. ?? 81. ????????????????????//?Single?node?on?list?? 82. ????????????????????if?(next?==?null)?? 83. ????????????????????????newTable[idx]?=?e;?? 84. ?? 85. ????????????????????else?{?? 86. ????????????????????????//?Reuse?trailing?consecutive?sequence?at?same?slot?? 87. ????????????????????????HashEntry?lastRun?=?e;?? 88. ????????????????????????int?lastIdx?=?idx;?? 89. ????????????????????????for?(HashEntry?last?=?next;?last?!=?null;?last?=?last.next)?{?? 90. ????????????????????????????int?k?=?last.hash?&?sizeMask;?? 91. ????????????????????????????if?(k?!=?lastIdx)?{?? 92. ????????????????????????????????lastIdx?=?k;?? 93. ????????????????????????????????lastRun?=?last;?? 94. ????????????????????????????}?? 95. ????????????????????????}?? 96. ????????????????????????newTable[lastIdx]?=?lastRun;?? 97. ?? 98. ????????????????????????//?Clone?all?remaining?nodes?? 99. ????????????????????????for?(HashEntry?p?=?e;?p?!=?lastRun;?p?=?p.next)?{?? 100. ????????????????????????????int?k?=?p.hash?&?sizeMask;?? 101. ????????????????????????????HashEntry?n?=?newTable[k];?? 102. ????????????????????????????newTable[k]?=?new?HashEntry(p.key,?p.hash,?n,?? 103. ????????????????????????????????????p.value);?? 104. ????????????????????????}?? 105. ????????????????????}?? 106. ????????????????}?? 107. ????????????}?? 108. ????????????table?=?newTable;?? 109. ????????}?? **size 方法** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. /**? 2. ?*?Returns?the?number?of?key-value?mappings?in?this?map.?If?the?map?contains? 3. ?*?more?than?Integer.MAX_VALUE?elements,?returns? 4. ?*?Integer.MAX_VALUE.?javadoc?上也寫明了,返回的數值不能超過Int的最大值,超過也返回最大值? 5. ?*?在下面的分析也可以看出,為了減少鎖競爭做了一些性能優化,這種的優化方式在很多方法都有使用? 6. ?*?? 7. ?*?@return?the?number?of?key-value?mappings?in?this?map? 8. ?*/?? 9. public?int?size()?{?? 10. ????final?Segment[]?segments?=?this.segments;?? 11. ????long?sum?=?0;?? 12. ????long?check?=?0;?? 13. ????int[]?mc?=?new?int[segments.length];?? 14. ????//?Try?a?few?times?to?get?accurate?count.?On?failure?due?to?? 15. ????//?continuous?async?changes?in?table,?resort?to?locking.?? 16. ????//?這里最多試RETRIES_BEFORE_LOCK=2?次的檢查對比?? 17. ????for?(int?k?=?0;?k? 18. ????????check?=?0;?? 19. ????????sum?=?0;//?size?總數?? 20. ????????int?mcsum?=?0;//?修改的總次數?? 21. ????????//?這里保存了一份對比值,供下次對比時使用?? 22. ????????for?(int?i?=?0;?i? 23. ????????????sum?+=?segments[i].count;?? 24. ????????????mcsum?+=?mc[i]?=?segments[i].modCount;?? 25. ????????}?? 26. ????????//?只有當map初始化的時候才等于0?? 27. ????????if?(mcsum?!=?0)?{?? 28. ????????????//?在此對比上面保存的修改值?? 29. ????????????for?(int?i?=?0;?i? 30. ????????????????check?+=?segments[i].count;?? 31. ????????????????if?(mc[i]?!=?segments[i].modCount)?{?? 32. ????????????????????check?=?-1;?//?force?retry?? 33. ????????????????????break;?? 34. ????????????????}?? 35. ????????????}?? 36. ????????}?? 37. ????????//?檢查和第一次保存值一樣則結束循環?? 38. ????????if?(check?==?sum)?? 39. ????????????break;?? 40. ????}?? 41. ????//?當不相等的時候,這里就只有用鎖來保證正確性了?? 42. ????if?(check?!=?sum)?{?//?Resort?to?locking?all?segments?? 43. ????????sum?=?0;?? 44. ????????for?(int?i?=?0;?i? 45. ????????????segments[i].lock();?? 46. ????????for?(int?i?=?0;?i? 47. ????????????sum?+=?segments[i].count;?? 48. ????????for?(int?i?=?0;?i? 49. ????????????segments[i].unlock();?? 50. ????}?? 51. ????//?這里也可以看出,如果超過int?的最大值值返回int?最大值?? 52. ????if?(sum?>?Integer.MAX_VALUE)?? 53. ????????return?Integer.MAX_VALUE;?? 54. ????else?? 55. ????????return?(int)?sum;?? 56. }?? **keys 方法** Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. ????public?Enumeration?keys()?{?? 2. ????????//這里新建了一個內部Iteraotr?類?? 3. ????????return?new?KeyIterator();?? 4. ????}?? 5. //這里主要是繼承了HashIterator?方法,基本的實現都在HashIterator?中?? 6. ????final?class?KeyIterator?extends?HashIterator?implements?Iterator,?? 7. ????????????Enumeration?{?? 8. ????????public?K?next()?{?? 9. ????????????return?super.nextEntry().key;?? 10. ????????}?? 11. ?? 12. ????????public?K?nextElement()?{?? 13. ????????????return?super.nextEntry().key;?? 14. ????????}?? 15. ????}?? 16. ?? 17. ????/*?----------------?Iterator?Support?--------------?*/?? 18. ????//?分析代碼發現,這個遍歷過程沒有涉及到鎖,查看Javadoc?后可知該視圖的?iterator?是一個“弱一致”的迭代器。。?? 19. ????abstract?class?HashIterator?{?? 20. ????????int?nextSegmentIndex;//?下一個分段的index?? 21. ????????int?nextTableIndex;//?下一個分段的容器的index?? 22. ????????HashEntry[]?currentTable;//?當前容器?? 23. ????????HashEntry?nextEntry;//?下個鍵值對?? 24. ????????HashEntry?lastReturned;//?上次返回的鍵值對?? 25. ?? 26. ????????HashIterator()?{?? 27. ????????????nextSegmentIndex?=?segments.length?-?1;?? 28. ????????????nextTableIndex?=?-1;?? 29. ????????????advance();?? 30. ????????}?? 31. ?? 32. ????????public?boolean?hasMoreElements()?{?? 33. ????????????return?hasNext();?? 34. ????????}?? 35. ?? 36. ????????//?先變量鍵值對的鏈表,再對table?數組的index?遍歷,最后遍歷分段數組的index。。這樣就可以完整的變量完所有的entry了?? 37. ????????final?void?advance()?{?? 38. ????????????//?先變量鍵值對的鏈表?? 39. ????????????if?(nextEntry?!=?null?&&?(nextEntry?=?nextEntry.next)?!=?null)?? 40. ????????????????return;?? 41. ????????????//?對table?數組的index?遍歷?? 42. ????????????while?(nextTableIndex?>=?0)?{?? 43. ????????????????if?((nextEntry?=?currentTable[nextTableIndex--])?!=?null)?? 44. ????????????????????return;?? 45. ????????????}?? 46. ????????????//?遍歷分段數組的index?? 47. ????????????while?(nextSegmentIndex?>=?0)?{?? 48. ????????????????Segment?seg?=?segments[nextSegmentIndex--];?? 49. ????????????????if?(seg.count?!=?0)?{?? 50. ????????????????????currentTable?=?seg.table;?? 51. ????????????????????for?(int?j?=?currentTable.length?-?1;?j?>=?0;?--j)?{?? 52. ????????????????????????if?((nextEntry?=?currentTable[j])?!=?null)?{?? 53. ????????????????????????????nextTableIndex?=?j?-?1;?? 54. ????????????????????????????return;?? 55. ????????????????????????}?? 56. ????????????????????}?? 57. ????????????????}?? 58. ????????????}?? 59. ????????}?? 60. ?? 61. ????????public?boolean?hasNext()?{?? 62. ????????????return?nextEntry?!=?null;?? 63. ????????}?? 64. ?? 65. ????????HashEntry?nextEntry()?{?? 66. ????????????if?(nextEntry?==?null)?? 67. ????????????????throw?new?NoSuchElementException();?? 68. ????????????//?把上次的entry換成當前的entry?? 69. ????????????lastReturned?=?nextEntry;?? 70. ????????????//?這里做一些預操作?? 71. ????????????advance();?? 72. ????????????return?lastReturned;?? 73. ????????}?? 74. ?? 75. ????????public?void?remove()?{?? 76. ????????????if?(lastReturned?==?null)?? 77. ????????????????throw?new?IllegalStateException();?? 78. ????????????ConcurrentHashMap.this.remove(lastReturned.key);?? 79. ????????????lastReturned?=?null;?? 80. ????????}?? 81. ????}?? **keySet/Values/elements 這幾個方法都和keys 方法非常相似**?。。就不解釋了。。而entrySet 方法有點特別。。我也有點不是很明白。。 Java代碼??![](https://box.kancloud.cn/2015-12-29_56824d379d348.png) 1. //這里沒什么好說的,看下就明白,主要在下面?? 2. public?Set>?entrySet()?{?? 3. ????????Set>?es?=?entrySet;?? 4. ????????return?(es?!=?null)???es?:?(entrySet?=?new?EntrySet());?? 5. ????}?? 6. ?? 7. ????final?class?EntrySet?extends?AbstractSet>?{?? 8. ????????public?Iterator>?iterator()?{?? 9. ????????????return?new?EntryIterator();?? 10. ????????}?? 11. }?? 12. //主要在這里,新建了一個WriteThroughEntry?這個類?? 13. ????final?class?EntryIterator?extends?HashIterator?implements?? 14. ????????????Iterator>?{?? 15. ????????public?Map.Entry?next()?{?? 16. ????????????HashEntry?e?=?super.nextEntry();?? 17. ????????????return?new?WriteThroughEntry(e.key,?e.value);?? 18. ????????}?? 19. ????}?? 20. ?? 21. ????/**? 22. ?????*?Custom?Entry?class?used?by?EntryIterator.next(),?that?relays?setValue? 23. ?????*?changes?to?the?underlying?map.? 24. ?????*?這個主要是返回一個Entry,但有點不明白的是為什么不在HashEntry中實現Map? 25. ?????*?.Entry就可以了(HashMap就是這樣的),為了減少鎖競爭??? 26. ?????*/?? 27. ????final?class?WriteThroughEntry?extends?AbstractMap.SimpleEntry?{?? 28. ????????WriteThroughEntry(K?k,?V?v)?{?? 29. ????????????super(k,?v);?? 30. ????????}?? 31. ?? 32. ????????/**? 33. ?????????*?Set?our?entry's?value?and?write?through?to?the?map.?The?value?to? 34. ?????????*?return?is?somewhat?arbitrary?here.?Since?a?WriteThroughEntry?does?not? 35. ?????????*?necessarily?track?asynchronous?changes,?the?most?recent?"previous"? 36. ?????????*?value?could?be?different?from?what?we?return?(or?could?even?have?been? 37. ?????????*?removed?in?which?case?the?put?will?re-establish).?We?do?not?and? 38. ?????????*?cannot?guarantee?more.? 39. ?????????*/?? 40. ????????public?V?setValue(V?value)?{?? 41. ????????????if?(value?==?null)?? 42. ????????????????throw?new?NullPointerException();?? 43. ????????????V?v?=?super.setValue(value);?? 44. ????????????ConcurrentHashMap.this.put(getKey(),?value);?? 45. ????????????return?v;?? 46. ????????}?? 47. ????}?? ? ?? 從上面可以看出,ConcurrentHash 也沒什么特別的,大概的思路就是采用分段鎖機制來實現的,把之前用一個容易EntryTable來裝的轉換成多個Table來裝鍵值對。而方法里面的也采用了不少為了減少鎖競爭而做的一些優化。。從ConcurrentHash類里面可以看出,它里面實現了一大堆的內部類。。比如Segment/KeyIterator/ValueIterator/EntryIterator等等。。個人覺得有些代碼好像比較難理解。。比如Segment 類繼承ReentrantLock,為什么不用組合呢。。還會有上面提到的,HashEntry 為什么不像HashMap 的Entry一樣實現Map.Entry接口。。建立這么多內部類,搞得人頭暈暈的。。。。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看