为什么HashMap和Hashtable方法有区别?

时间:2013-11-27 07:13:54

标签: java hashmap hashtable

我想知道putHashMap

中的Hashtable方法差异

HashTable放置方法代码

Entry tab[] = table;
     int hash = key.hashCode();
     int index = (hash & 0x7FFFFFFF) % tab.length;
     for (Entry<K,V> e = tab[index] ; e != null ; e = e.next) {
         if ((e.hash == hash) && e.key.equals(key)) {
             V old = e.value;
             e.value = value;
             return old;
         }
     }

HashMap放置方法代码

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;
         }
     }

为什么hashtable有不同的代码来查找索引?

int index = (hash & 0x7FFFFFFF) % tab.length;

虽然hashMap具有jdk设计者提供的hash()功能。

2 个答案:

答案 0 :(得分:0)

二进制文件中的0x7FFFFFFF是什么?它是01111111111111111111111111111111

请注意,最左边的0。这意味着该数字始终为正(因为最左边的为零)。由于&,使用此二进制文件的每个数字&将是非负数,因为:

01111111111111111111111111111111
Anything                          &
--------------------------------
0 ← Always

在此之后,%运算符用于确保我们处于tab.length范围内。

您没有发布HashMap如何生成索引的实现。我不认为这是非常不同的。毕竟他们有一个非常相似的逻辑。

HashMap拨打indexFor正在执行:return h & (length-1);

重要提示:HashTable早于HashMap,难怪存在差异化实施。

答案 1 :(得分:0)

哈希表:

int index = (hash & 0x7FFFFFFF) % tab.length;

表示: hash - 没有最左边的位(符号)模数表长度

HashMap中:

int i = indexFor(hash, table.length);

正在致电:

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

表示模数长度为1 那里没有太大的区别,实际上modulo length-1意味着我们可以获得的最大值是长度为2。在这里,长度-1确保我们不会遇到我们将获得0xFFFFFFFF的情景,实际上我们可能得到的最高值将是0xFFFFFFFE

区别在于低位(在HashMap中的HashMap与高位)。现在我们应该(递归地)问为什么。答案隐藏在hash()方法中,该方法出现在代码的第一行(上图)中,它也与HashTable实现不同:

int hash = hash(key.hashCode());

并在hash() method

中找到了解释
           /**
  258      * Applies a supplemental hash function to a given hashCode, which
  259      * defends against poor quality hash functions.  This is critical
  260      * because HashMap uses power-of-two length hash tables, that
  261      * otherwise encounter collisions for hashCodes that do not differ
  262      * in lower bits. Note: Null keys always map to hash 0, thus index 0.
  263      */
  264     static int hash(int h) {
  265         // This function ensures that hashCodes that differ only by
  266         // constant multiples at each bit position have a bounded
  267         // number of collisions (approximately 8 at default load factor).
  268         h ^= (h >>> 20) ^ (h >>> 12);
  269         return h ^ (h >>> 7) ^ (h >>> 4);
  270     }
  271