Java踩坑记系列之Arrays.AsList
java.util.Arrays
的asList
方法可以方便的将数组转化为集合,我们平时开发在初始化ArrayList
时使用的比较多,可以简化代码,但这个静态方法asList()
有几个坑需要注意:
一. 如果对集合使用增加或删除元素的操作将会报错
如下代码:
List list = Arrays.asList("a","b","c");
list.add("d");
输出结果:
Exception in thread "main" java.lang.UnsupportedOperationException
at java.util.AbstractList.add(AbstractList.java:148)
at java.util.AbstractList.add(AbstractList.java:108)
at ArraysAsListTest.main(ArraysAsListTest.java:7)
Arrays.asList
的源码虽然返回的是一个ArrayList
,但这个ArrayList
是Arrays内部的一个静态类(java.util.Arrays.ArrayList
),并不是我们平时用的java.util.ArrayList
只是名字一样,包名不一样:
这个ArrayList
也继承自AbstractList
,但是却没有实现add()
,remove()
方法用这两个方法其实调用的是AbstractList
的默认方法:
public void add(int index, E element) {
throw new UnsupportedOperationException();
}
直接抛出" UnsupportedOperationException
"的异常!
所以当我们调用这个ArrayList
的add
方法时其实是调用了抽象集合类里的add
方法,就抛出了上面的异常,原因是数组虽然提供了转集合的方法, 但本质上还是个数组,数组的长度是固定的,所以jdk的作者没有实现add()
和remove()
方法。
大家在使用的时候需要注意,要结合具体业务场景判断:如果只是对转成后的集合进行遍历或使用stream()流操作都没有问题,可以正常使用(修改元素也没问题) 但如果需要新增元素或删除元素等改变集合长度的操作就要避免,否则报错就会影响到我们正常的业务逻辑。
二. 长度问题
还是Arrays
的asList()
,该方法无法将一个基本类型的数组转换成集合List,或者说基本类型虽然能转换成功,但不是"我们想要的集合",因为asList
方法接收的是一个泛型的变长参数。
而基本数据类型是无法被泛型化的,这样的话对于泛型而言,基本数据类型会被作为一个"[x"的类型,"["表示这是一个数组,"x"为当前数组的类型,例如: int[] 实际上它的类型是"[I"
这样的话Arrays.asList
传入的参数是基本类型的话,会把数组当做一个元素处理(长度=1),如果我们要遍历List
或获取List
的长度就不准确了,类似下面的用法:
int array[] = {1,2,3,4,5};
List list = Arrays.asList(array);
System.out.println("长度="+list.size());
System.out.println("是否含有元素3="+list.contains(3));
输出结果:
长度=1
是否含有元素3=false
如果我们的代码里用到了这样获取长度或判断是否包含指定元素的操作就要注意写法,否则就会影响我们的逻辑流程!
为避免这样的问题出现,有很多种其他写法,比如将array转成包装类(即引用类型),如下:
Integer array[] = {1,2,3,4,5};
List list = Arrays.asList(array);
System.out.println("长度="+list.size());
System.out.println("是否含有元素3="+list.contains(3));
输出结果:
长度=5
是否含有元素3=true
当然也可以使用google的集合类"Ints.asList",如下:
int array[] = {1,2,3,4,5};
List list = Ints.asList(array);
System.out.println("长度="+list.size());
System.out.println("是否含有元素3="+list.contains(3));
输出结果:
长度=5
是否含有元素3=true
但是google的Ints.asList
方法返回的list也是一个自己实现的集合,同样不支持add
和remove
方法,如果既要保证转换成list后的数据长度正确又要能增删操作的话,就用java.util.ArrayList吧。
三. Arrays.asList方法返回的是数组的一个视图,也就是说对这个list的操作都会反映在原数组上
文章来源:http://javakk.com/132.html
本文由博客群发一文多发等运营工具平台 OpenWrite 发布
最新文章
- [恶趣味]搞了下局域网内的arp网络欺骗
- java源码分析:Arrays.sort
- background-image小解
- 爱上MVC3~为下拉列表框添加一个自定义验证规则
- C#如何实现一个简单的流程图设计器
- WSGI服务器实践二--实践一个基本功能的WSGI服务器
- C#多线程与异步的区别
- 2016年10月30日 星期日 --出埃及记 Exodus 19:15
- Windows 上远程访问 Unix 的 XWindow / XManager / X
- 【vijos1266】搜集环盖
- Ubuntu安装Osmocom-BB一只猿多频点WEB脚本
- Collection集合之六大接口(Collection、Set、List、Map、Iterator和Comparable)
- ubuntu14.04编译mono源码(有坑...)
- 网站如何做到完全不需要jQuery
- jquery文本折叠
- Linux Shell编程(5)——shell特殊字符(下)
- 【Javaweb】笔面试题 ---(1)
- spring之注解详解
- js收藏代码
- [UOJ UNR#2 UOJ拯救计划]
热门文章
- spring Boot面试题(2020最新版)
- linux操作系统网卡漂移导致网络不可用
- ZooKeeper-3.5.6分布式锁
- 细嚼JS闭包知识点及案例分析
- Spring 配置文件AOP
- Go-The process cannot access the file because it is being used by another process.
- [iTyran原创]iPhone中OpenGL ES显示3DS MAX模型之一:OBJ格式分析
- 01 百度 AI Studio 基础操作记录(一) Notebook
- Linux系统编程—有名管道
- Doug Lea在J.U.C包里面写的BUG又被网友发现了