1、HashMap构造方法

 HashMap<String, String> map = new HashMap<>();    public HashMap() {            this(DEFAULT_INITIAL_CAPACITY, DEFAULT_LOAD_FACTOR);        }

空的构造方法默认调用有参结构

DEFAULT_INITIAL_CAPACITY 默认大小 16DEFAULT_LOAD_FACTOR 默认加载因子 0.75
 public HashMap(int initialCapacity, float loadFactor) {        //做参数校验 加载因子 容量大小         (大于0 小于等于MAXIMUM_CAPACITY)        this.loadFactor = loadFactor;        threshold = initialCapacity;        init();    }

2、put办法

map.put("k1", "v1");//put办法public V put(K key, V value) {        if (table == EMPTY_TABLE) {            inflateTable(threshold);        }        if (key == null)            return putForNullKey(value);        int hash = hash(key);        int i = indexFor(hash, table.length);        for (Entry<K,V> e = table[i]; e != null; e = e.next) {            Object k;            if (e.hash == hash && ((k = e.key) == key || key.equals(k))) {                V oldValue = e.value;                e.value = value;                e.recordAccess(this);                return oldValue;            }        }        modCount++;        addEntry(hash, key, value, i);        return null;    }
2.1 inflateTable办法
    /**     * Inflates the table.     */    private void inflateTable(int toSize) {        // Find a power of 2 >= toSize        //该办法用于寻找一个大于或等于该数的一个2的幂次方数,        //为前期扩容或计算元素寄存地位        int capacity = roundUpToPowerOf2(toSize);        threshold = (int) Math.min(capacity * loadFactor, MAXIMUM_CAPACITY + 1);        table = new Entry[capacity];        initHashSeedAsNeeded(capacity);    }
2.1.1 roundUpToPowerOf2办法
private static int roundUpToPowerOf2(int number) {        // assert number >= 0 : "number must be non-negative";        int rounded = number >= MAXIMUM_CAPACITY                ? MAXIMUM_CAPACITY                : (rounded = Integer.highestOneBit(number)) != 0                    ? (Integer.bitCount(number) > 1) ? rounded << 1 : rounded                    : 1;        return rounded;    }  /**   * 该办法用于返回一个小于等于i的一个2的幂次方数   * 采纳的的办法为最高为 1  */public static int highestOneBit(int i) {        // HD, Figure 3-1        i |= (i >>  1);        i |= (i >>  2);        i |= (i >>  4);        i |= (i >>  8);        i |= (i >> 16);        //这里i得出为 00....0 1111        //i >>> 1   00....0 0111        //减去失去   00....0 1000        return i - (i >>> 1);    }
该办法就是讲hash值与对应的Entry数组的长度进行与运算  static int indexFor(int h, int length) {        // assert Integer.bitCount(length) == 1 : "length must be a non-zero power of 2";        return h & (length-1);    }
final int hash(Object k) {        int h = hashSeed;        if (0 != h && k instanceof String) {            return sun.misc.Hashing.stringHash32((String) k);        }        h ^= k.hashCode();        // This function ensures that hashCodes that differ only by        // constant multiples at each bit position have a bounded        // number of collisions (approximately 8 at default load factor).        //为了让数组元素寄存的更加散列让高位也参加运算        h ^= (h >>> 20) ^ (h >>> 12);        return h ^ (h >>> 7) ^ (h >>> 4);    }
2.2 addEntry办法
 void addEntry(int hash, K key, V value, int bucketIndex) {        //当寄存元素个数超过容量*加载因子 且以后下标为        bucketIndex的table曾经寄存过元素则扩容        if ((size >= threshold) && (null != table[bucketIndex])) {            resize(2 * table.length);            hash = (null != key) ? hash(key) : 0;            bucketIndex = indexFor(hash, table.length);        }        createEntry(hash, key, value, bucketIndex);    }
2.2.1 createEntry() 办法
   void createEntry(int hash, K key, V value, int bucketIndex) {        Entry<K,V> e = table[bucketIndex];        //这里实现的逻辑就是将 新的Entry对象        的next指向table[bucketIndex] 以后寄存的元素,        而后将table[bucketIndex] 指向新的Entry对象        table[bucketIndex] = new Entry<>(hash, key, value, e);        size++;    }
2.2.2 resize() 办法
    // newCapacity为之前数组元素长度的两倍    void resize(int newCapacity) {    //转移元素到新数组        transfer(newTable, initHashSeedAsNeeded(newCapacity));    }
/**     * Initialize the hashing mask value. We defer initialization until we     * really need it.     */     //该办法就是为了从新生成hahs种子    final boolean initHashSeedAsNeeded(int capacity) {        //这里hashSeed之前默认为0 所以为false        boolean currentAltHashing = hashSeed != 0;        boolean useAltHashing = sun.misc.VM.isBooted() &&                (capacity >= Holder.ALTERNATIVE_HASHING_THRESHOLD);        //所以这里只有当useAltHashing返回true        //才会从新计算hashSeed        boolean switching = currentAltHashing ^ useAltHashing;        if (switching) {            hashSeed = useAltHashing                ? sun.misc.Hashing.randomHashSeed(this)                : 0;        }        return switching;    }
transfer 办法
    void transfer(Entry[] newTable, boolean rehash) {        int newCapacity = newTable.length;        //遍历以后Entry数组以及链表 即遍历所有元素        //这里在并发环境下,会呈现循环列表的状况        //所以在get或put的时候就可能会导致死循环        for (Entry<K,V> e : table) {            while(null != e) {                Entry<K,V> next = e.next;                if (rehash) {                    e.hash = null == e.key ? 0 : hash(e.key);                }                int i = indexFor(e.hash, newCapacity);                e.next = newTable[i];                newTable[i] = e;                e = next;            }        }    }