HashMap:1.7采用的是数组加链表实现,1.8采用的是数组加链表再加红黑树实现。当链表的长度大于等于8时,用红黑树代替链表。因为链表的查询效率低,通过遍历获取数据慢,但是链表的增加修改效率高。
Hashtable:采用的是数组加链表实现
HashMap:线程不安全,多线程操作可能会导致数据丢失。
Hashtable:线程安全,在put、get等方法上通过synchronized,给所有的数组加了一个锁,保证了数据安全,但是会导致put、get效率很低,保证了同时只能put或者get一个值。
HashMap:初始数组大小为16,设置的初始数组大小为2的幂次方,为了保证key的hash值与初始数组大小减1的与运算的结果在0到初始数组大小减1的范围内(因为0到n-1为数组下标,保证数组不越界)。
Hashtable:设置的初始数组大小为11,它是通过key的hash值与int的最大值取与运算的结果再与设置的初始数组大小取余运算得到下标。因为要与初始数组大小取余,所以下标一定会在(0到n-1)
HashMap与Hashtable的加载因子都为0.75
HashMap与Hashtable扩容的条件都为数组容量(存了多少数据)大于等于数组大小乘加载因子,但是HashMap是把数组扩大为原来两倍,Hashtable扩大两倍还要加1,
HashMap1.7先扩容再加数据,1.8先加数据再扩容,Hashtable先扩容后加数据
HashMap:Put原理:先得到key的hash值,然后对得到的hash值进行右移(为了保证高位数据影响数组的索引,扩大数据分散),然后与数据大小与运算得到数组索引。1.7直接把数据加载到链表的头部,next指向当前的第一个元素。1.8就需要判断当前索引对应的下面是链表还是红黑树,如果是红黑树,打乱红黑树的结构,重组新的红黑树,如果是链表,判断当前链表+1的长度是不是大于等于7,是就将链表重组成新的红黑树。否在就把数据加到链表尾部。
Hashtable:Put原理:先得到key的hash值,然后将得到的hash值与int类型最大值取与运算,得到的结果再与数组大小求余,得到数组大小,然后加到链表头部,next指向当前第一个元素
HashMap:key可以为null,为table[0]的值
Hashtable:key不可以为null,否则报空指针。
HashMap:继承AbstractMap抽象类,Hashtable:继承Dictionary抽象类,都实现Map接口