基于jdk1.8,从源码中获取的总结
linklist | arraylist | |
源码展示及说明 | public class LinkedList<E> extends AbstractSequentialList<E>
Deque: 支持两端元素插入和移除的线性集合 AbstractSequentialList: 继承了AbstractList类,其方法是用ListIterator和Iterator(迭代器)实现对元素的增删改管理。 | public class ArrayList<E> extends AbstractList<E> implements List<E>, RandomAccess, Cloneable, java.io.Serializable
RandomAccess接口: List实现使用,支持快速随机访问 |
实现 | 对象node实现,包含:前一个元素,元素本身,下一个元素。 transient :字段的生命周期仅存于调用者的内存中 | 数组对象实现(查询快,增删慢)。 |
扩容 | 一个一个相加 | 源码:oldCapacity + (oldCapacity >> 1), 1,默认大小为10,然后1.5倍左右扩容, 2,设定为0的时候,前四次每次加1,第五次开始1.5倍扩容 3,最大长度为Integer 的最大值减 8。 |
实际容量 | 数量取自内存中对象的 size属性的变动 | 数量取自数组的动态大小变动 |
增删 | 增删操作后,重新制定当前元素的前一个对象,后一个对象,更新size,first,last对应的node数据。 尾部增加和删除 O(1)复杂度 指定位置增加 O(n)复杂度 | 增删操作后,要先计算容量,容量不足或者容量过大,需要重新调整容量大小,然后将数据复制到新的内存,并将新的元素加到旧数组后面。 尾部增加 O(1)复杂度 指定位置增加和删除O(n)复杂度 |
查询 | 依赖node对象的pre和next属性,一个一个查找。下标小于长度的一半,就从前往后找,反之,从后往前找。 O(n)复杂度 | 根据数组下标,一个一个查找。O(1)复杂度 |
有趣点 | transient :字段的生命周期仅存于调用者的内存中 全局属性:size(大小),first(第一个元素),last(最后更新的元素) 三个变量随着增删动态变换,非真实数据存储位置,满足类需要 | transient :字段的生命周期仅存于调用者的内存中 全局属性:elementData 数组变量随着增删动态变换,即真实数据存储位置 |
优势 | 适合增删 | 适合查询 |
linklist中有意思的事情
每个元素对象包括三个属性:prev(前一个对象),item(当前对象),next(下一个对象)。以: prev & item & next
一个值时:null & v1 & null
两个值时:null & v1& v2 v1 & v2 & null
三个值时:null & v1 & v2 v1 & v2 & v3 v2 & v3 & null
中间新增value4时:null & v1& v2 v1 & v2 & v4 v2 & v4 & v3 v4 & v3 & null
尾部新增value4时:null & v1& v2 v1 & v2 & v3 v2 & v3 & v4 v3 & v4 & null
尾部删除value4时:null & v1& v2 v1 & v2 & v3 v2 & v3 & null null & null & null
中间删除value3时:null & v1& v2 v1 & v2 & v4 null & null & null v2 & v4 & null
删除掉某个数据对象时,是将该对象置空
根据适用场景自行选择使用,没有假设只有结论的比较毫无意义