我们再来通过例子探究一下>
(移位运算符):>>1 右移一位相当于除 2,右移 n 位相当于除以 2 的 n 次方 。这里 oldCapacity 明显右移了 1 位所以相当于 oldCapacity /2 。对于大数据的 2 进制运算,位移运算符比那些普通运算符的运算要快很多,因为程序仅仅移动一下而已,不去计算,这样提高了效率,节省了资源
grow()
方法 :- 当 add 第 1 个元素时,oldCapacity 为 0,经比较后第一个 if 判断成立,newCapacity = minCapacity(为 10) 。但是第二个 if 判断不会成立,即 newCapacity 不比 MAX_ARRAY_SIZE 大,则不会进入
hugeCapacity
方法 。数组容量为 10,add 方法中 return true,size 增为 1 。 - 当 add 第 11 个元素进入 grow 方法时,newCapacity 为 15,比 minCapacity(为 11)大,第一个 if 判断不成立 。新容量没有大于数组最大 size,不会进入 hugeCapacity 方法 。数组容量扩为 15,add 方法中 return true,size 增为 11 。
- 当第16个元素进入容器时再次扩容
- java 中的
length
属性是针对数组说的,比如说你声明了一个数组,想知道这个数组的长度则用到了 length 这个属性. - java 中的
length()
方法是针对字符串说,如果想看这个字符串的长度则用到length()
这个方法. - java 中的
size()
方法是针对泛型集合说的,如果想看这个泛型有多少个元素,就调用此方法来查看!
hugeCapacity()
从上面
grow()
方法源码我们知道: 如果新容量大于 MAX_ARRAY_SIZE,进入(执行) hugeCapacity()
方法来比较 minCapacity 和 MAX_ARRAY_SIZE,如果 minCapacity 大于最大容量,则新容量则为Integer.MAX_VALUE
,否则,新容量大小则为 MAX_ARRAY_SIZE 即为 Integer.MAX_VALUE - 8
。private static int hugeCapacity(int minCapacity) {if (minCapacity < 0) // overflowthrow new OutOfMemoryError();//对minCapacity和MAX_ARRAY_SIZE进行比较//若minCapacity大,将Integer.MAX_VALUE作为新数组的大小//若MAX_ARRAY_SIZE大,将MAX_ARRAY_SIZE作为新数组的大小//MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;return (minCapacity > MAX_ARRAY_SIZE) ?Integer.MAX_VALUE :MAX_ARRAY_SIZE;}
System.arraycopy()
和 Arrays.copyOf()
阅读源码的话,我们就会发现 ArrayList 中大量调用了这两个方法 。比如:我们上面讲的扩容操作以及
add(int index,E element)
、toArray()
等方法中都用到了该方法!// 我们发现 arraycopy 是一个 native 方法,接下来我们解释一下各个参数的具体意义/***复制数组* @param src 源数组* @param srcPos 源数组中的起始位置* @param dest 目标数组* @param destPos 目标数组中的起始位置* @param length 要复制的数组元素的数量*/public static native void arraycopy(Object src,intsrcPos,Object dest,int destPos,int length);
场景:/*** 在此列表中的指定位置插入指定的元素 。*先调用 rangeCheckForAdd 对index进行界限检查;然后调用 ensureCapacityInternal 方法保证capacity足够大;*再将从index开始之后的所有成员后移一个位置;将element插入index位置;最后size加1 。*/public void add(int index,E element) {rangeCheckForAdd(index);ensureCapacityInternal(size + 1);// Increments modCount!!//arraycopy()方法实现数组自己复制自己//elementData:源数组;index:源数组中的起始位置;elementData:目标数组;index + 1:目标数组中的起始位置; size - index:要复制的数组元素的数量;System.arraycopy(elementData,index,elementData,index + 1,size - index);elementData[index] = element;size++;}
经验总结扩展阅读
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Java单例模式,看这一篇就够了
- 感恩节祝福寄语精选
- 微信支付v3接口的 官方 Java SDK
- Java函数式编程:二、高阶函数,闭包,函数组合以及柯里化
- 精选600个 冯姓女孩名字2023年属兔
- 精选600个 韩姓女孩名字2023年属兔
- 精选600个 唐姓女孩名字2023年属兔
- 精选600个 罗姓女孩名字2023年属兔
- 精选600个 马姓女孩名字2023年属兔
- 精选600个 谢姓女孩名字2023年属兔