ArrayList源码分析

ArrayList继承了AbstractList类,实现了List接口。

默认的大小为10,所有元素值保存在一个Object数组内。


add方法

  在ArrayList内,有两个add方法,分别如下图。

  • add(E e)方法:首先确保Capacity可以容纳下加一个元素,然后将下一个元素赋值为e,返回true代表添加成功。
  • add(int index, E element):首先通过rangeCheckForAdd判断index是否满足要求,然后确保可以容纳下加一个元素,然后调用System.arraycopy将从index开始的元素向后赋值一个元素位置,最后将index位置的元素赋值为element。由于需要移动index开始的所有元素,所以在本方法代价很高。

ensureCapacity、ensureCapacityInternal、ensureExplicitCapacity方法



  • 这里主要看grow方法,一般先将Capacity扩充到之前的1.5倍,若小于minCapacity ,则赋值为minCapacity ,若大于MAX_ARRAY_SIZE ,则赋最大值,最后将新的容量的数组赋值给原来的数组。

addAll方法

  在ArrayList内,有两个addAll方法,分别如下。

  • addAll(Collection<? extends E> c):本方法可在ArrayList后增加一个Collection内的所有元素。List、Queue、Set都实现了Collection接口。本方法主要通过System.arraycopy将Collection中元素复制到本ArrayList中。
  • addAll(int index, Collection<? extends E> c):如果index在size范围内,那么首先将从index开始的元素向后移动,然后将Collection内元素复制到本ArrayList。

clear方法

  • 本方法直接清空ArrayList内所有元素,并将size置为0。

set方法

  • 首先验证set方法的index,保证小于size,然后保存旧值,赋新值,最后返回旧值。

get方法

  • 首先验证index,保证小于size,然后返回下标为index的元素。

contains方法和indexOf方法

  • contains内调用indexOf方法,若o为null,则判断在ArrayList中是否有元素等于null,否则判断是否有元素与o相同,有则返回元素下标,否则返回-1,以此来判断该元素是否包含于ArrayList。

remove方法



  • remove(int index):首先确保index满足条件,在size范围内,然后将index之后的元素向前移动一位,将之前的最后一个元素置为null,size减少1,返回旧值。
  • remove(Object o):如果删除值为null,先遍历所有元素,若有元素为null则删除,否则看是否有元素与所删除元素相同,有相同者则删除。删除调用fastRemove函数,也是将被删除元素后的所有元素向前移动一位,然后将原来最后一个元素置为null,size减少1。

removeAll方法和retainAll方法



  • removeAll(Collection<?> c):将c中所有存在的元素从本ArrayList中移除。调用batchRemove方法,将所有需要保存的元素存在elementData前部分,w的最后值为要保存元素的数量。r!=size是为了确保没有出错,若r!=size,则前面抛出了异常,接着将从r开始的size-r个元素复制到ArrayList后面。如果w==size,则表示没有删除,否则将w之后的元素清空。
  • retainAll(Collection<?> c):将ArrayList中所有在c中存在的元素保留。与上述方法类似,调用batchRemove方法,将所有需要保存的元素保存在elementData前部分,后序也如同上述过程。

posted on 2017-02-18 00:05  liuyang0  阅读(172)  评论(0编辑  收藏  举报

导航

Flag Counter