Arrays.toList 方法详解
Arrays.ArrayList 的元素存储区的声明
从声明上可以看出 Arrays.ArrayList 中的元素存储数据是一个不可变的数组,由于数组的长度本身是不可变的,所以 Arrays.ArrayList 从元素存储上就不支持长度变化。
Arrays.ArrayList 方法接收基本数据类型数据
由于 Arrays.ArrayList 参数为可变长泛型,而基本数据类型是无法泛型化的,所以它把 int[] arr 数组当成了一个泛型对象,所以集合中最终只有一个元素 arr。
替代方法:可以由我们下文所讲的 Collections.singletonList() 去替代
public static void main(String[] args) {
int[] arr = {1,2,3};
List<int[]> ints = Collections.singletonList(arr);
}
Arrays.ArrayList 方法使用 add 和 remove 方法
在使用 Arrays.ArrayList 返回的集合使用 add 方法时,抛出 UnsupportedOperationException 错误,带着疑问我们查看源码可知:
经过查看 asList底层源码,asList 内部类并没有重写 add,remove 等方法,所以它会调用父类 AbstractList 的方法,而父类的方法中抛出的却是异常信息
如果我们想使用 Add 和 remove 方法,可以在重新 new ArrayList<>() 集合,再将 Arrays.asList(arr) 放入进去
Collections.singletonList 方法详解
singletonList方法主要用于只有一个元素的优化,减少内存分配,无需分配额外的内存,可以从SingletonList内部类看得出来,由于只有一个element,因此可以做到内存分配最小化(可以参考上文的替代方法)。
通过源码注释可知:该方法返回的集合是immutable(只读),如果调用add 或者 remove 方法时,将会抛出 UnsupportedOperationException
总结
- 对于声明方式,都是用如下方式:(xxxxList ==> SingletonList,ArrayList)
private static class xxxxList<E>
extends AbstractList<E>
implements RandomAccess, Serializable {
- 两者调用add 和remove方法时,都会报 java.lang.UnsupportedOperationException,因为都继承了 AbstractList 抽象类,而且两者的内部类并没有重写 add 和 remove 方法。