日期:2014-05-20  浏览次数:20745 次

JAVA HashMap是怎么解决冲突的?
1.Java 1.6源代码的HashMap,get数据或者put数据的时候,会产生冲突吗?
2.如果产生了冲突,是如何解决的?使用的开放地址法?链地址法?或者其他?
为了方便说明,我假定现在已经有一个Map myMap = new HashMap(),一个有6条数据,其中第2个位置上面有3个数据,如图:


附上HashMap的源码:
    public V put(K key, V value) {
        if (key == null)
            return putForNullKey(value);
        int hash = hash(key.hashCode());
        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;
    }

开始问问题了:
1.现在如果我想添加一个元素Key1-Value1,计算出来的hashCode是2,那现在这个元素放到哪里呢?放到元素B的下面?HashMap的源码里面是怎么实现这个的呢?
2.addEntry(hash, key, value, i);是什么意思呢?什么时候会用到呢?

下面是get方法:
    public V get(Object key) {
        if (key == null)
            return getForNullKey();
        int hash = hash(key.hashCode());
        for (Entry<K,V> e = table[indexFor(hash, table.length)];
             e != null;
             e = e.next) {
            Object k;
            if (e.hash == hash && ((k = e.key) == key || key.equals(k)))
                return e.value;
        }
        return null;
    }

3.如果myMap.get(2),我现在想要的是B元素,HashMap里面是怎么处理的呢?e.next是循环整个map还是只循环key=2的这个链表呢?


请高手耐心解答。。。不胜感激。。。
如果有描述不清楚的,请指教
------解决方案--------------------
总体上是链地址法,先执行hash,再执行equals。
处理冲突倒不是很复杂,无非是遍历一个链表,最后调用“头插法”,比较精髓的是这个函数:

 static int hash(int h) {
        // 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);
    }

还有这个函数:

    static int indexFor(int h, int length) {  
        return h & (length-1);  
    }  

纯位运算的内容,参考:  http://zhangshixi.iteye.com/blog/672697