Java 集合框架(二)—— ArrayList
二、数组列表 —— ArrayList
1、构造方法
ArrayList 是 Java 中的动态数组,底层实现就是对象数组,只不过数组的容量会根据情况来改变。
它有个带 int 类型参数的构造方法,根据传入的参数,扩展初始化的数组容量,这个方法是推荐使用的,因为如果预先知道数组的容量,可以设置好初始值,而不用等每次容量不够而扩容,减少 Arrays.copyOf 的次数:
它的很多方法的实现都是依靠 Arrays 这个工具类完成的,足以体现它与数组之间的密切关系。
比如有个带 Collection 类型的构造方法,实现如下:
2、常用方法
1) trimToSize 方法
Trims the capacity of this ArrayList instance to be the list's current size.
An application can use this operation to minimize the storage of an ArrayList instance.
该方法可以去掉 ArrayList 占用的多余的空间或内存,因为 ArrayList 每次扩容后总会有所剩余,如果数组很大,占用的多余的空间会比较大,内存不够时可以使用此方法。
2)ensureCapacity 方法
public void ensureCapacity(int minCapacity)
Increases the capacity of this ArrayList instance, if necessary, to ensure that it can hold at least the number of elements specified by the minimum capacity argument.
除了在初始化 ArrayList 的时候可以事先定义一个给定的容量之外,还可以用此方法提高 ArrayList 的初始化速度。看下面的例子:
public static void main(String[] args) { int n = 100000; String str = "hello google"; // 没有调用 ensureCapacity() 方法初始化 ArrayList 对象 ArrayList<String> list = new ArrayList<>(); long startTime = System.currentTimeMillis(); for (int i = 0; i <= n; i++) { list.add(str); } long endTime = System.currentTimeMillis(); System.out.println("time: " + (endTime - startTime) + " ms"); // 调用 ensureCapacity() 方法初始化 ArrayList 对象 list = new ArrayList<>(); startTime = System.currentTimeMillis(); list.ensureCapacity(n); for (int i = 0; i < n; i++) { list.add(str); } endTime = System.currentTimeMillis(); System.out.println("time: " + (endTime - startTime) + " ms"); }
结果为:
3)isEmpty 方法
注意此方法是判断是否为空,不是是否为 null
public boolean isEmpty() { return size == 0; }
4)indexOf 、lastIndexOf 和 contain 方法
indexOf 方法返回 list 中首次出现给定对象的索引值(从 0 开始),如果不存在则返回 -1。
lastIndexOf 方法返回 list 中最后一次出现给定对象的索引值(从 size - 1 开始),如果不存在则返回 -1。
contain 方法 参数为 Object o,判断 list 中是否包含给定的对象,存在则返回 true,源码如下:
5)add,get 和 set 方法
三个很简单的方法,区别在于:add 方法是数组长度 +1,将给定对象放在最后的位置,set 方法是替换指定索引位置的元素,get 方法则是获取指定索引位置的元素。
6)remove 方法
删除指定索引位置的元素或者指定元素,不推荐使用,对数组操作比较复杂,如果你使用了此方法,说明你应该考虑用 LinkedList 了。
3、最佳使用建议
1)ArrayList 是 Array 的复杂版本
ArrayList 内部封装了一个 Object 类型的数组,从一般的意义来说,它和数组没有本质的差别,甚至于 ArrayList 的许多方法,如 Index、IndexOf、Contains、Sort 等都是在内部数组的基础上直接调用 Array 的对应方法。
2)内部的 Object 类型的影响
对于一般引用类型来说,这部分的影响不大,但是对于值类型,往 ArrayList 里面添加和修改元素,都会引起装箱和拆箱操作,频繁的操作可能会影响一部分效率。
3)数组扩容
这是对 ArrayList 效率影响比较大的一个因素。
每当执行 Add、AddRange、Insert、InsertRange 等添加元素的方法,都会检查内部数组的容量是否不够了,如果是,它就会以当前容量的两倍来重新构建一个数组,将旧元素 Copy 到新数组中,然后丢弃旧数组,在这个临界点的扩容操作,应该来说是比较影响效率的。
例 1:比如,一个可能有 200 个元素的数据动态添加到一个以默认 16 个元素大小创建的 ArrayList 中,将会经过:
16*2*2*2*2 = 256
四次的扩容才会满足最终的要求,那么如果一开始就以 ArrayList list = new ArrayList(210) 的方式创建 ArrayList,不仅会减少 4 次数组创建和 Copy 的操作,还会减少内存使用。
例 2:预计有 30 个元素而创建了一个 ArrayList:
ArrayList List = new ArrayList(30);
在执行过程中,加入了 31 个元素,那么数组会扩充到 60 个元素的大小,而这时候不会有新的元素再增加进来,而且有没有调用 TrimSize 方法,那么就有 1 次扩容的操作,并且浪费了 29 个元素大小的空间。如果这时候,用 ArrayList list = new ArrayList(40) 那么一切都解决了。
所以说,正确的预估可能的元素,并且在适当的时候调用 TrimSize 方法是提高 ArrayList 使用效率的重要途径。
特别感谢:
2、《Thinking In Java》
3、《Core Java Volume I》
Java 集合框架(二)—— ArrayList的更多相关文章
- Java集合框架之ArrayList浅析
Java集合框架之ArrayList浅析 一.ArrayList综述: 位于java.util包下的ArrayList是java集合框架的重要成员,它就是传说中的动态数组,用MSDN中的说法,就是Ar ...
- (Set, Map, Collections工具类)JAVA集合框架二
Java集合框架部分细节总结二 Set 实现类:HashSet,TreeSet HashSet 基于HashCode计算元素存放位置,当计算得出哈希码相同时,会调用equals判断是否相同,相同则拒绝 ...
- java 集合框架(二)Iterable接口
Iterable接口是java 集合框架的顶级接口,实现此接口使集合对象可以通过迭代器遍历自身元素,我们可以看下它的成员方法 修饰符和返回值 方法名 描述 Iterator<T> iter ...
- Java——集合框架之ArrayList,LinkedList,迭代器Iterator
概述--集合框架 Java语言的设计者对常用的数据结构和算法做了一些规范(接口)和实现(具体实现接口的类).所有抽象出来的数据结构和操作(算法)统称为Java集合框架(Java Collection ...
- Java集合框架(二)
Set Set:无序,不可以重复元素. |--------HashSet:数据结构是哈希表. 线程是非同步的.保证元素唯一性的原理是:判断元素的hashCode值是否相同,如果相同,还会继续判断元素的 ...
- java集合框架03——ArrayList和源码分析
最近忙着替公司招人好久没写了,荒废了不好意思. 上一章学习了Collection的架构,并阅读了部分源码,这一章开始,我们将对Collection的具体实现进行详细学习.首先学习List.而Array ...
- Java集合框架(一)-ArrayList
大佬理解->Java集合之ArrayList 1.ArrayList的特点 存放的元素有序 元素不唯一(可以重复) 随机访问快 插入删除元素慢 非线程安全 2.底层实现 底层初始化,使用一个Ob ...
- java集合框架05——ArrayList和LinkedList的区别
前面已经学习完了List部分的源码,主要是ArrayList和LinkedList两部分内容,这一节主要总结下List部分的内容. List概括 先来回顾一下List在Collection中的的框架图 ...
- 深入理解java集合框架之---------Arraylist集合 -----添加方法
Arraylist集合 -----添加方法 1.add(E e) 向集合中添加元素 /** * 检查数组容量是否够用 * @param minCapacity */ public void ensur ...
- java集合框架之ArrayList
参考http://how2j.cn/k/collection/collection-arraylist/363.html 使用数组的局限性 一个长度是10的数据:Hero[] heroArr=new ...
随机推荐
- Amazon成本和产出的衡量方式
Amazon用一种T-Shirt Size 估计的方式来做项目. 产品经理会对每一条需求评估上业务影响力的尺寸,如:XXXL 影响一千万人以上或是可以占到上亿美金的市场,XXL,影响百万用户或是占了千 ...
- IDEA14添加SVN
今天升级IDEA14,发现SVN变了,折腾了好一会才搞好.记录一下,希望其他人能少走弯路.主要是IDEA14的svn是用命令行工具进行操作,这样对以后SVN的兼容性也会好很多,这个在他们官方的博客上也 ...
- shell 脚本 删除文件内容为空的文件
#!/bin/bask # cd /tmp for a in * ;do if [ ! -s $a ] ;then #[ ! -s $a ] 文件为空返回为真 rm -rf $a fi done 测试 ...
- 高并发Web
hadoop适合处理分布式集群系统,本身是支持高速并发海量数据的写入和读取的.解决大量用户并发访问的方案有很多,给你个千万pv的参考方案:1)架构中直接引入软件名称的模块,是个人推荐使用的,如Hapr ...
- Team Foundation Server (TFS)集成Flyway,实现数据库的版本管理
1 概述 在系统开发过程中,我们对软件源代码的版本管理,已经有了比较成熟的解决方案.通过使用TFVC或GIT等源代码管理工具,可以非常方便的对软件代码实现回退.比较.分支合并等版本操作.对于软件依赖的 ...
- (转)(WinForm)FormBorderStyle属性
原地址
- Pipelines - .NET中的新IO API指引(三) 边看边记
Pipelines - .NET中的新IO API指引 作者 marcgravell 原文 此系列前两篇网上已有的译文 Pipelines - .NET中的新IO API指引(一) Pipeline ...
- c# is 和 as 的区别和使用
1:is 是判断类型,用于检查对象是否与给定类型兼容,不成功则不会抛出异常,如果兼容则返回true,如果不兼容则返回false.在进行类型转换之前用 f (P_obj is System.String ...
- 什么是fortran语言之fortran语言入门
Fortran源自于“公式翻译”(英语:FormulaTranslation)的缩写,是一种编程语言.它是世界上最早出现的计算机高级程序设计语言,广泛应用于科学和工程计算领域.FORTRAN语言以其特 ...
- click 版本升级7.0踩过的坑
click 版本升级7.0踩过哪些坑? click 版本6.7升级至7.0以上,包名由 click 变更为 Click click 的 Options 和 Parameters 规则变更为如下: Fo ...