Hashmap源码解析-扩容函数

系列目录

  1. 总览&目录
  2. 链表节点NODE
  3. 构造函数
  4. 扩容函数
  5. put
  6. remove
  7. get
  8. 遍历
  9. &hashtable

扩容函数

1.更新容量和阈值,

​ if cap>0, 不超过上限的情况下cap、thre都乘2

​ if cap=0, oldThr>0, 说明初始化的时候赋初始容量参数了,newCap=oldThr

​ if cap=0, oldthr=0, 直接重新初始化,cap=16,thre=12

2.更新哈希桶, 遍历原桶

​ if 只有一个节点,直接挪过去

​ if 链表有超过8个节点,是红黑树, 复杂, 再说todo

​ if 少于8个的链表,则可能挪到低位,也可能挪到高位,看它本身hash在新容量时应在哪里,代码中巧妙通过与oldCap & 的方式判断需改到高还是低,具体在代码注释中有

concurrentmodificationexception源码解析

Java安全开发手册中
  • 7. 【强制】不要在 foreach 循环里进行元素的 remove/add 操作。remove 元素请使用 Iterator 方式,如果并发操作,需要对 Iterator 对象加锁。
个人总结
  • 在迭代器中走list的remove大部分情况都会抛 ConcurrentModificationException 异常,从迭代器的next、remove中抛出,因new迭代器类的时候,私有变量expectedModCount会记录修改次数,当List的modCount不一致时会抛出异常,而List的add,remove等修改操作都会增加modCount

  • 也会有在删除某些元素后导致迭代器cursor和size正好相等,hasnext返回false, 不再遍历就不抛异常,但不会遍历到后面移动到已删除位置的元素

  • List接口中有iterator()接口,因此List的子类都要注意这点

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×