java arraylist源码记录
1. ArrayList 实现了RandomAccess接口, RandomAccess接口用于标记是否可以随机访问
2. 继承了AbstractList类, 因此获取了modcount , modcount用于实现快速失败机制, 如果list有修改, 那么modcount自增
3. ArrayList不支持并发, 是非线程安全的
4. 支持存放null元素
5. 扩容, 每次都是原来大小的1.5倍
public void ensureCapacity(int minCapacity) {
//如果elementData不等于EMPTY_ELEMENTDATA(因为初始化时有可能等于), 那么minExpand为0或者DEFAULT_CAPACITY
//如果elementData不为空minExpand为0, 可以用这个来处理minCapacity为负数的情况
//如果elementData为空, 那么就是默认容量
int minExpand = (elementData != EMPTY_ELEMENTDATA)
// any size if real element table
? 0
// larger than default for empty table. It's already supposed to be
// at default size.
: DEFAULT_CAPACITY;
//如果最小容量大于minExpand, 那么进行明确扩容
if (minCapacity > minExpand) {
ensureExplicitCapacity(minCapacity);
}
}
//已确定扩容minCapacity
private void ensureExplicitCapacity(int minCapacity) {
modCount++; //修改次数加1
// overflow-conscious code
if (minCapacity - elementData.length > 0)
grow(minCapacity);
}
private void grow(int minCapacity) {
// overflow-conscious code
int oldCapacity = elementData.length;
//newCapacity为oldCapacity的1.5倍, 这里有可能会溢出为-1
int newCapacity = oldCapacity + (oldCapacity >> 1);
....
}
6. lastIndexOf, contains, indexOf方法用于查找, 时间复杂度均为O(N), 使用对象的equals方法进行比较
7. clone() 方法为深复制, 所谓深复制和浅复制的区别在于复制内部引用对象时的不同, 深复制会将原来的对象重新clone一份, 让复制对象的引用指向新对象, 而浅复制仅仅复制引用, 仍指向原来的对象. java Object中的clone方法为浅复制
8. set() 和 get() 为O(1)的时间复杂度
9. 调用ensureCapacityInternal(int) 会使modCount+1. ArrayList中的添加元素都会调用这个函数 ,例如add(object)和add(int,Object)
10. add(Object) 和add(int,Object)的时间复杂度为O(N), 因为底层数组的复制移动
11. remove(int)方法也会使modCount+1, 时间复杂度为O(N) , 同时内部使用elementData[--size] = null;用来防止内存泄漏, 以便gc释放内存
12. remove(Object) 使用了fastRemove非法, fastRemove如果未找到删除元素, 那么modCount是不会变的, 反之modCount+1 , 之所以fastRemove称之为fast是因为使用了System.arrayCopy进行元素移动, System.arrayCopy是一个native方法, 可以躲避java访问数组时的下标检查.
13. clear方法, modCount+1
14. addAll(...) 都会调用ensureCapacityInternal方法, 从而使modCount+1, O(N)的时间复杂度
15. removeAll(object)//补集和retainAll(object)//交集 都可以使用batchRemove方法, O(N^2)的时间复杂度, modCount+1.
16. 快速失败机制体现在容器的遍历中, Iterator会在对象初始化过程中保存当前容器的modCount, 并在每次遍历检查modCount, 如果两者不一致, 那么说明容器在遍历时被修改, 抛出ConcurrentModificationException.
private class Itr implements Iterator<E> {
int expectedModCount = modCount;
public E next() {
checkForComodification();
int i = cursor;
...
}
public void remove() {
...
checkForComodification();
...
}
final void checkForComodification() {
if (modCount != expectedModCount)
throw new ConcurrentModificationException();
}
}
java arraylist源码记录的更多相关文章
- Java ArrayList源码剖析
转自: Java ArrayList源码剖析 总体介绍 ArrayList实现了List接口,是顺序容器,即元素存放的数据与放进去的顺序相同,允许放入null元素,底层通过数组实现.除该类未实现同步外 ...
- Java ArrayList源码分析(有助于理解数据结构)
arraylist源码分析 1.数组介绍 数组是数据结构中很基本的结构,很多编程语言都内置数组,类似于数据结构中的线性表 在java中当创建数组时会在内存中划分出一块连续的内存,然后当有数据进入的时候 ...
- Java ArrayList源码分析(含扩容机制等重点问题分析)
写在最前面 这个项目是从20年末就立好的 flag,经过几年的学习,回过头再去看很多知识点又有新的理解.所以趁着找实习的准备,结合以前的学习储备,创建一个主要针对应届生和初学者的 Java 开源知识项 ...
- Java - ArrayList源码分析
java提高篇(二一)-----ArrayList 一.ArrayList概述 ArrayList是实现List接口的动态数组,所谓动态就是它的大小是可变的.实现了所有可选列表操作,并允许包括 nul ...
- Java——ArrayList源码解析
以下针对JDK 1.8版本中的ArrayList进行分析. 概述 ArrayList基于List接口实现的大小可变的数组.其实现了所有可选的List操作,并且元素允许为任意类型,包括null元 ...
- Java|ArrayList源码分析|add()增加方法和grow()扩容方法
本文结构: 1.介绍特点 2.基本方法 3.重点源码分析 1.介绍特点 ArrayList: 是List的一个具体实现子类,是List接口的一个数组实现 (里面必定维护了一个数组). 默认初始容量10 ...
- java ArrayList源码分析(转载)
1.ArrayList是一个相对来说比较简单的数据结构,最重要的一点就是它的自动扩容,可以认为就是我们常说的“动态数组”. 来看一段简单的代码: 12345 ArrayList<String&g ...
- 【源码阅读】Java集合之一 - ArrayList源码深度解读
Java 源码阅读的第一步是Collection框架源码,这也是面试基础中的基础: 针对Collection的源码阅读写一个系列的文章,从ArrayList开始第一篇. ---@pdai JDK版本 ...
- Java集合源码分析(一)ArrayList
前言 在前面的学习集合中只是介绍了集合的相关用法,我们想要更深入的去了解集合那就要通过我们去分析它的源码来了解它.希望对集合有一个更进一步的理解! 既然是看源码那我们要怎么看一个类的源码呢?这里我推荐 ...
随机推荐
- NOIP2017赛前模拟(3):总结
题目: 1.购买板凳(100) 大意:区间修改最后查询全局最大值; 2.新排序(40分暴力) 大意:给一串长度小于100000的数列···每次操作找出序列中严格小于其左边的数字或者严格大于其右边的数字 ...
- LineageOS源码定制手机系统
LineageOS源码定制手机系统 导语: 现在市场的手机基本就两种: 苹果机和android机. 今天我们不谈苹果机, 对小编我来讲,那是个奢侈品, android是我的最爱.对于一般androi ...
- TransactionProxyFactoryBean 配置问题
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.spr ...
- Team Contests - Warmup(2016年多校热身赛,2016年黑龙江省赛)
Team Contests - Warmup A 题意:... 思路:不会 代码:... 随机 B 题意:给n个点,问是否有一个圆上有最少n/3个点 思路:随机大法好. 代码:... 递推 C 题意: ...
- docker mysql 导入导出数据
导出数据 1.导出mysql单张表结构和数据: docker exec -it my-mysql mysqldump dbname -uroot -p123456 --tables tname > ...
- 51nod 1201 整数划分
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1201 DP转移方程:dp[i][j] = dp[i-j][j]+dp[i ...
- (40)C#windows服务控制
ServiceController类 可以使用 ServiceController 类连接到现有服务并控制其行为. 构造函数 1.ServiceController () ServiceControl ...
- [转] DataSet的的几种遍历
1. 多表多行多列的情况 foreach (DataTable dt in YourDataset.Tables) //遍历所有的datatable { foreach (DataRow dr in ...
- [转] 32位 PL/SQL Develope r如何连接64位的Oracle 图解
原文地址:LINK 由于硬件技术的不断更新,Win7系统逐渐成为主流,而且计算机内存逐渐增大,为了充 分的利用内存资源(因为32为系统最多只能用到3G左右的内存),提高系统性能,很多人开始使用Win7 ...
- fastscript增加公共函数
fastscript增加公共函数 unit fs_BsCommFuncs; interface{$i fs.inc}uses SysUtils, Classes, fs_iclassesrtti, f ...