1. The source code

final Node<K,V>[] resizeNewCap * - If the table size exceeds MAXIMUM_CAPACITY(1<<30), do not expand the table size * - otherwise double the table size (2 * oldCap <30). MAXIMUM_CAPACITY && oldCap > 16) newThr = oldThr << 1; * 2. oldThr > 0 (initial capacity was placedinThreshold) * - where oldCap == 0, indicating that the table is empty but oldThr, all newCap = oldThr; * 2. OldCap == 0&& oldThr == 0 (zero initial threshold using defaults) * -newcap = DEFAULT_INITIAL_CAPACITY(16) * -newthr = 16 * 0.75 = 12 * 4. If newThr == 0, find a new threshold and assign threshold */ Node<K,V>[] oldTab = table; int oldCap = (oldTab == null) ? 0 : oldTab.length; int oldThr = threshold; int newCap, newThr = 0;if (oldCap > 0) {
            if (oldCap >= MAXIMUM_CAPACITY) { 
                threshold = Integer.MAX_VALUE;
                return oldTab;
            }
            else if ((newCap = oldCap << 1) < MAXIMUM_CAPACITY &&
                     oldCap >= DEFAULT_INITIAL_CAPACITY)
                newThr = oldThr << 1; // double threshold
        }
        else if (oldThr > 0) // initial capacity was placed in threshold
            newCap = oldThr;
        else {               // zero initial threshold signifies using defaults
            newCap = DEFAULT_INITIAL_CAPACITY;
            newThr = (int)(DEFAULT_LOAD_FACTOR * DEFAULT_INITIAL_CAPACITY);
        }
        if (newThr == 0) {
            float ft = (float)newCap * loadFactor;
            newThr = (newCap < MAXIMUM_CAPACITY && ft < (float)MAXIMUM_CAPACITY ? (int)ft : Integer.MAX_VALUE); } threshold = newThr; // Declare a new size array @suppressWarnings ({"rawtypes"."unchecked"})
            Node<K,V>[] newTab = (Node<K,V>[])new Node[newCap];
        table = newTab;
        if(oldTab ! = null) {for (int j = 0; j < oldCap; ++j) {
                Node<K,V> e;
                if((e = oldTab[j]) ! = null) {// Old set to null for GC oldTab[j] = null; // If only one nodeif(e.ext == null) // There is only one element, get the new subscript, note that newCap is used // here note the new JDk1.8hashThe function is: high 16bit unchanged, low 16bit and high 16bit do an xor, and then (n-1) &hashObtain the subscript newTab[e.hash & (newcap-1)] = e; // If it is a red-black treeelse if (e instanceof TreeNode)
                        ((TreeNode<K,V>)e).split(this, newTab, j, oldCap);
                    else{// preserve order /** * First, some concepts. After capacity expansion, the capacity is doubled, so there will be low and high, low is the original length, such as (0-15), high (16-31) */ // 1. Node<K,V> loHead = null, loTail = null; Node<K,V> hiHead = null, hiTail = null; // 2. Temporary Node Node<K,V> next;do{ next = e.next; // 3. Use the bit operation to determine the high and low bits, == 0 indicates < oldCap, which belongs to the low level, as shown in the following analysisif((e.hash & oldCap) == 0) { // 4. // loTail == null;if (loTail == null)
                                    loHead = e;
                                elseloTail.next = e; loTail = e; } // 5else {
                                if (hiTail == null)
                                    hiHead = e;
                                elsehiTail.next = e; hiTail = e; }}while((e = next) ! = null); // The low value is in the original indexif(loTail ! = null) { loTail.next = null; newTab[j] = loHead; } // The high value is in the new indexif(hiTail ! = null) { hiTail.next = null; newTab[j + oldCap] = hiHead; } } } } }return newTab;
    }
Copy the code

2. How to determine index (E. Hash & oldCap) after capacity expansion

1 << 4 = 2^4 = 16 1 << 4 << 1 = 32 1 << 4 << 1 = 32 In the old index j 2. hash2, the high value is 1, 1&1 = 1, and the high value is 1, which is equivalent to j + oldCap. Therefore, the expansion does not need to recalculate the hash value, but only need to judge the original hash value and oldCap bit operation, and use the high value to determineCopy the code

16 Expand the capacity to 32:

Here’s an example from E.Hash & oldCap:

Map map = new HashMap<>(8,0.75f);
map.put("1"."1");
map.put("2"."2");
map.put("3"."3");
map.put("10"."10");
map.put("18"."18");
map.put("6"."6");
map.put("Seven"."Seven");
map.put("8"."8");
System.out.println(map);
Copy the code
The initial size is 8, the load factor is 0.75F, the length reaches 7 will expand, The debug will find that oldCap = 8 and the hash value of 10 is 1567 0110 0001 1111 0000 0000 1000 and the hash value of 18 is 1575 0110 0010 0111 0000 0000 1000 And operation = 0 lowCopy the code

-HashMap resize()